'Workbook.open' error - Closes the file right after opening it - vba

I need to get data on one hundred Excel workbooks. I created a macro to loop through those files, get the data and close them. But right after my Workbooks.open(path) opens the file, it closes it and throws a 1004 error saying that the method 'open' failed.
I tried to open another of those one hundred files and every one of them throws the same error. I tried to open a normal file (not one of those one hundred), through the macro, it opens normally.
Copied a bunch of those to my C:\, all of them throw an error.
Recorded a macro to open the file. The file opens because I clicked File->Open File, but it throws an error if I run the macro to open it.
Obviously the problem lies in those files.
LINK to the file.
--> CODE:
Just a normal Workbook.open code (There is no full code, it's just it! And I get an error with the file linked)
Workbook.Open("C:\file.xlsx")
--> They Open normally by hand without any error or problem.
--> They have:
* Querytables
* Normal formulas
* They are kinda small
--> Observations and what I tried:
The paths are right (it opens the file and closes it right after, and error).
The files I'm trying to open have connection queries, but I deleted the connections on my test files. Same error.
Tried the CurruptLoad param, same error (I don't know if I used it right).
Tried UpdateLinks:=0, same error.
Tried to open it through new Excel.Application, nothing changed.
Tried on another PC, same thing.
Anyone had something like this?
What should I try?

What are you doing after the open ?
If you are trying to do something else, then maybe file has not opened completely and error is based on next line not happening.

Solution I found for this case (here in my work)
Application.DisplayAlerts = False
set wb = Workbooks.Open(objFile.path, ReadOnly:=True, CorruptLoad:=xlExtractData)
wb.close
Application.DisplayAlerts = True
Through the CorruptLoad:=xlExtractData, it clear every table, every connection, and anything else that could be problem. I get my data and close the file without saving it.
Thanks for the support guys.

If I understand your problem you can use one code that I use when I need to retrieve data from plus files (all with the same formatting )
Sub ImportData()
Dim wb As Workbook
Dim myPath As String
Dim myFile As String
Dim myExtension As String
Dim FldrPicker As FileDialog
Dim LastRow As Long
'Optimize Macro Speed
Application.ScreenUpdating = False
Application.EnableEvents = False
Application.Calculation = xlCalculationManual
WsTo = ActiveWorkbook.Name
'Retrieve Target Folder Path From User
Set FldrPicker = Application.FileDialog(msoFileDialogFolderPicker)
With FldrPicker
.Title = "Select A Target Folder"
.AllowMultiSelect = False
If .Show <> -1 Then GoTo NextCode
myPath = .SelectedItems(1) & "\"
End With
'In Case of Cancel
NextCode:
myPath = myPath
If myPath = "" Then Exit Sub
'Target File Extension (must include wildcard "*")
myExtension = "*.xlsx"
'Target Path with Ending Extention
myFile = Dir(myPath & myExtension)
'Loop through each Excel file in folder
Do While myFile <> ""
'Set variable equal to opened workbook
Set wb = Workbooks.Open(Filename:=myPath & myFile)
'Change First Worksheet's Background Fill Blue
Sheets(1).Select
Range("A1").Select
Range(Selection, Selection.End(xlDown)).Select
Range(Selection, Selection.End(xlToRight)).Select
Selection.Copy
WsFrom = ActiveWorkbook.Name
Windows(WsTo).Activate
Sheets(1).Select
With ActiveSheet
LastRow = .Cells(.Rows.Count, "A").End(xlUp).Row
End With
Range("A" & LastRow + 1).Select
Selection.PasteSpecial Paste:=xlPasteValues, Operation:=xlNone, SkipBlanks _
:=False, transpose:=False
Application.CutCopyMode = False
'Save and Close Workbook
Workbooks(WsFrom).Close SaveChanges:=False
'Get next file name
myFile = Dir
Loop
'Message Box when tasks are completed
MsgBox "Importazione completata!"
'Reset Macro Optimization Settings
Application.ScreenUpdating = True
Application.EnableEvents = True
Application.Calculation = xlCalculationAutomatic
End Sub

Related

Copy and Paste VALUES from multiple workbooks to a worksheet in another workbook / Paste Value within Loop

The heavy lifting of this problem has already been solved here:
Copy and paste data from multiple workbooks to a worksheet in another Workbook
After adapting the code, I got everything to work perfectly in about 15 minutes. However, I then spent the past 3 hours scouring stackoverflow and the rest of the internet trying to figure out how to get it to paste VALUES ONLY instead of bringing over the formatting and formulas with it.
I've tried using .PasteSpecial xlPasteValues, but every time I try this I get an error that says "Compile Error: Expected: end of statement"
I've also tried using .PasteSpecial(xlPasteValues), I get an error that says "Run-time error '1004': Unable to get the PasteSpecial property of the Range class"
My concern is that neither of these methods will work since there wasn't even a .Paste function to begin with.
So when I tried to just add .Paste, it gives me a "Run-time error '438': Object doesn't support this property or method"
Here's the whole code, but I'm mainly just trying to figure out how to do exactly the same with except pasting VALUES ONLY. Thanks!
Sub ConsolidateAllOrdenes()
Dim wb As Workbook
Dim myPath As String
Dim myFile As String
Dim myExtension As String
Dim FldrPicker As FileDialog
Dim lRow As Long
Dim ws2 As Worksheet
Dim y As Workbook
'Optimize Macro Speed
Application.ScreenUpdating = False
Application.EnableEvents = False
Application.Calculation = xlCalculationManual
'Retrieve Target Folder Path From User
Set FldrPicker = Application.FileDialog(msoFileDialogFolderPicker)
With FldrPicker
.Title = "Choose Target Folder Path"
.AllowMultiSelect = False
If .Show <> -1 Then GoTo NextCode
myPath = .SelectedItems(1) & "\"
End With
'In Case of Cancel
NextCode:
myPath = myPath
If myPath = "" Then GoTo ResetSettings
'Target File Extension (must include wildcard "*")
myExtension = "*.xlsm*"
'Target Path with Ending Extention
myFile = Dir(myPath & myExtension)
Set y = Workbooks.Open("C:\Consolidado\Consolidado_2018-09-05a.xlsm")
Set ws2 = y.Sheets("Consolidado_Orden")
'Loop through each Excel file in folder
Do While myFile <> ""
'Set variable equal to opened workbook
Set wb = Workbooks.Open(Filename:=myPath & myFile)
'Copy data on "Orden de Compras" sheet to "consolidado_orden" Sheet in other workbook
With wb.Sheets("Orden de Compras")
lRow = .Range("C" & Rows.Count).End(xlUp).Row
.Range("A5:M" & lRow).Copy ws2.Range("A" & Rows.Count).End(xlUp).Offset(1, 0)
End With
wb.Close SaveChanges:=False
'Get next file name
myFile = Dir
Loop
'Message Box when tasks are completed
MsgBox "I hope that worked!"
ResetSettings:
'Reset Macro Optimization Settings
Application.EnableEvents = True
Application.Calculation = xlCalculationAutomatic
Application.ScreenUpdating = True
End Sub
Replace your copy/paste with this:
With wb.Sheets("Orden de Compras")
Range("A2:M" & Cells(Rows.Count, "A").End(xlUp).Row).Copy
ws2.Range("A" & Rows.Count).End(xlUp).Offset(1, 0).PasteSpecial Paste:=xlPasteValues
End With
Sorry, I'm new to this, but I think I finally figured it out. I believe the range with the copy was lacking a defined workbook and sheet.
Once I specified the workbook and sheet for the copy, there was no issue with putting the paste range on another line and adding .PasteSpecial Paste:=xlPasteValues.
I was also copying 2 lines from each workbook that didn't actually have anything, so I added If WorksheetFunction.CountA(wb.Sheets("Orden de Compras").Range("C5:C200")) <> 0 Then and later Else and End If to skip that workbook if it didn't have anything within the range C5:C200.
I also added Application.CutCopyMode = False because a message box kept popping up after each file.
Replace the copy/paste with this:
With wb.Sheets("Orden de Compras")
If WorksheetFunction.CountA(wb.Sheets("Orden de Compras").Range("C5:C200")) <> 0 Then
lRow = .Range("C" & Rows.Count).End(xlUp).Row
wb.Sheets("Orden de Compras").Range("A5:M" & lRow).Copy
ws2.Range("A" & Rows.Count).End(xlUp)(2).PasteSpecial Paste:=xlPasteValues
Application.CutCopyMode = False
Else
End If
End With
Thanks to everyone and especially #GMalc for the help!!!

VBA run from my PERSONAL wb is perfect, copied to a distro wb and it breaks. Why?

I have the following code in a macro in my personal book, and it works perfectly.
I'm trying to copy it into the actual wb it's running from so I can send it around for others to use, and it's breaking at the commented line "XXXXXX". The selected wb is being opened fine, but none of the subsequent editing occurs to that book. All of the following code (deletion of columns, etc) that should be happening to the opened workbook only happens to the wb running the macro, which is...sub-optimal.
I don't know why! Any thoughts welcomed.
Thank you
Sam
Sub PredictBoxValue()
Dim wb As Workbook
Dim myPath As String
Dim myFile As String
Dim myExtension As String
Dim FldrPicker As FileDialog
Dim TitleName As String
Dim sas As String
Dim sos As String
Dim unusedRow As Long
Dim filename As String
'Optimize Macro Speed
Application.ScreenUpdating = False
'Application.EnableEvents = False
'Application.Calculation = xlCalculationManual
'Retrieve Target Folder Path From User
sos = ActiveWorkbook.Name
ActiveSheet.Range("B11", "AF11").Clear
Dim fNameAndPath As Variant
fNameAndPath = Application.GetOpenFilename(FileFilter:="Excel Files (*.XLS),
*.XLS", Title:="Select File To Be Opened")
If fNameAndPath = False Then Exit Sub
Set wb = Workbooks.Open(fNameAndPath)
sas = ActiveWorkbook.Name
'Delete extraneous columns and rows
'XXXXXXXXXXX
TitleName = Cells(5, 2).Value
Columns(8).Delete
Columns(12).Delete
Columns(12).Delete
Columns(3).Delete
Columns(2).Delete
Columns(1).Delete
Rows(3).Delete
Rows(2).Delete
Rows(1).Delete
Here:
Do Until Cells(2, 1).Value = "1"
Range("A1").End(xlDown).Select
'Do Until ActiveCell.Value = "1"
'ActiveCell.Offset(1).Select
'Loop
Do While ActiveCell.Value < 1
ActiveCell.EntireRow.Delete
ActiveCell.Offset(-1, 0).Select
Loop
ActiveCell.Offset(-1, 1).Select
Do While ActiveCell.Offset(0, -1).Value > 30
ActiveCell.EntireRow.Delete
GoTo Here
Loop
ActiveCell.Resize(, 7).Cut ActiveCell.Offset(1, 0).End(xlToRight).Offset(0,
1)
ActiveCell.EntireRow.Delete
Loop
Rows(1).EntireRow.Delete
Cells(1, 1) = TitleName
Range("A1", Range("A1").End(xlToRight)).Copy
Windows(sos).Activate
ActiveSheet.Cells(11, 2).PasteSpecial (xlPasteValues)
Application.CutCopyMode = False
Windows(sas).Activate
'Save and Close Workbook
wb.Close SaveChanges:=False
Windows(sos).Activate
ActiveSheet.Cells(5, 3).Select
'Message Box when tasks are completed
MsgBox ("Data uploaded for ") & Range("B11")
ResetSettings:
'Reset Macro Optimization Settings
Application.EnableEvents = True
Application.Calculation = xlCalculationAutomatic
Application.ScreenUpdating = True
End Sub
I took a bit of a closer look at your code. I think you are saying that you want to run code from macros.xlsm (or something like that), and have it operate on mydata.xlsx (or some such). Therefore, in your macro, ThisWorkbook will refer to macros.xlsm (should you need to refer to that).
After you have done Set wb = Workbooks.Open(fNameAndPath) to open mydata.xlsx, only and always refer to wb and wb.Sheets("whatever") when you are talking about mydata.xlsx.
Don't use Columns, Rows, Sheets, or Cells without a sheet reference in front of them
Don't use ActiveWorkbook/ActiveWorksheet at all.
Instead of ActiveCell, use a named range, e.g., as in this answer to the question BruceWayne noted.
That should take care of it!
<soapbox>And, in general, please be careful of your indentation and use longer variable names — both will help you avoid bugs as you work on this code.</soapbox>

Create loop to open multiple files and copy data to a master file in VBA excel

I have multiple files with data that need to be transposed into a single master file with all the data into a single row.
I'm a complete noob in programming so if the code I have so far doesn't make any sense, then please feel free to change it
I was able to find this "Loop all excel files in a folder" code from www.TheSpreadsheetGuru.com The code works perfectly fine, it will open up each file individually in the folder and then close it, and then open the next file and close it until it has gone through every file in that folder.
However, I'd like to insert a "copy and paste data" code loop within the loop. So what needs to happen is, the code will open "File1" in the folder, and then copy and paste the data into the "Master File" in cell A4. Then it will close "File1", and then open up "File2" and copy the data into "Master File" in cell A5 and then close "File2". It will repeat this until all files in the folder have been opened/closed.
This is the code I have right now, but I can't get the copy and paste code to work properly. I'm having a hard time figuring out how to set the loop up where the code will know what file it is currently on and setting a counter for the cell of the Master File that it is pasting into.
Sub LLoopAllExcelFilesInFolder()
'PURPOSE: To loop through all Excel files in a user specified folder and perform a set task on them
'SOURCE: www.TheSpreadsheetGuru.com
Dim wb As Workbook
Dim myPath As String
Dim myFile As String
Dim myExtension As String
Dim FldrPicker As FileDialog
'Optimize Macro Speed
Application.ScreenUpdating = False
Application.EnableEvents = False
Application.Calculation = xlCalculationManual
'Retrieve Target Folder Path From User
Set FldrPicker = Application.FileDialog(msoFileDialogFolderPicker)
With FldrPicker
.Title = "March"
.AllowMultiSelect = False
If .Show <> -1 Then GoTo NextCode
myPath = .SelectedItems(1) & "\"
End With
'In Case of Cancelhow
NextCode:
myPath = myPath
If myPath = "" Then GoTo ResetSettings
'Target File Extension (must include wildcard "*")
myExtension = "*.xlsx"
'Target Path with Ending Extention
myFile = Dir(myPath & myExtension)
'Loop through each Excel file in folder
Do While myFile <> ""
'Set variable equal to opened workbook
Set wb = Workbooks.Open(Filename:=myPath & myFile)
'THIS IS MY COPY AND PASTE CODE (DOESN'T WORK)
Dim row As Integer
While row = 4
Workbooks("Filename:=myPath & myFile").Worksheets("Resin Log").cell("I5") = Workbooks("Workbook1.xlsm").Worksheets("Sheet1").Range("A" & row).Value
Next row
'Save and Close Workbook
wb.Close SaveChanges:=False
'Get next file name
myFile = Dir
Loop
'Message Box when tasks are completed
MsgBox "Task Complete!"
ResetSettings:
'Reset Macro Optimization Settings
Application.EnableEvents = True
Application.Calculation = xlCalculationAutomatic
Application.ScreenUpdating = True
End Sub
It is possible to do what you're talking about. I would suggest, trying to just set cell values in the file being created directly
targetworkbook.worksheets(1).Range("A1").value = sourceworkbook.Worksheets(1).Range("C4").value
rather than using .Copy & .Paste so that if the macro takes a while to run you aren't locked out of using Copy/Paste in other applications. If you're still unsure of what to do, try doing it with Record Macro turned on. The generated code will need tweaked, but will give you most of what you need.
Also, be sure to look at this link for some other things to avoid using in your code.

Open many files in a folder apply a macro and save them to a different folder with different names like 1, 2, 3

I am trying to write code on VBA that allows me to access all files in a predetermined folder 1. Open each file, apply a macro of interest, then copy the end result to a different workbook in a predetermined folder 2 save them there as .csv files
The problem with my code is that it is a problem when I am saving the workbook added to the predetermined folder 2. I am always saving it with the same name which creates an overlapping.
The other problem is when I try to close wb.close (see my code below) I am getting the save changes y/n prompt.
enter image description here
I already wrote a code and failed miserably. I need expert help. Thank you again for all your support.
Best
Rami
Sub LoopFile()
'Enable reference to Microsoft Scripting Runtime if you want to use early binding
Dim fso As Object 'Scritping.FileSystemObject
Dim fldr As Object 'Scripting.Folder
Dim file As Object 'Scripting.File
Dim wb As Workbook
Set fso = CreateObject("Scripting.FileSystemObject")
Set fldr = fso.GetFolder("D:\Rami Chehab\University Degrees & Courses\PhD in Labour Economics\Data\Data 2016\UNCTAD\1\nOT DONE COUNTRIES\")
For Each file In fldr.Files
'Open the file
Set wb = Workbooks.Open(file.Path)
'## You will need to modify this line to refer to the correct
' module name and macro name:
Application.Run "PERSONAL.XLSB!Ramroum"
Cells.Select
Range("F7").Activate
Application.CutCopyMode = False
Selection.Copy
Workbooks.Add
ActiveSheet.Paste
Application.CutCopyMode = False
' The problem here it is only saving the folder as name 1 and not changing for example for 1 then in the other loop to 2, 3 and so on and so forth
' I think I need your help here in my code
ChDir _
"D:\Rami Chehab\University Degrees & Courses\PhD in Labour Economics\Data\Data 2016\UNCTAD\Okay"
ActiveWorkbook.SaveAs Filename:= _
"D:\Rami Chehab\University Degrees & Courses\PhD in Labour Economics\Data\Data 2016\UNCTAD\Okay\1.xlsx" _
, FileFormat:=xlOpenXMLWorkbook, CreateBackup:=False
ActiveWindow.Close
'Close the file (it was saved in Macro6 already)
wb.Close
Next
Set file = Nothing
Set fldr = Nothing
Set fso = Nothing
End Sub
Put Application.DisplayAlerts = False near the top of your Sub. The put Application.DisplayAlerts = True at the end of your sub.
I think I did something to a certain extent right and here is my new code. However, I still can not tell excel not to ask me whether you like to save the file or not when I write wb.close
Anyways here is my code
Sub Ram2()
'Enable reference to Microsoft Scripting Runtime if you want to use early binding
Dim fso As Object 'Scritping.FileSystemObject
Dim fldr As Object 'Scripting.Folder
Dim file As Object 'Scripting.File
Dim wb As Workbook
Dim i As Integer
i = 1
Set fso = CreateObject("Scripting.FileSystemObject")
Set fldr = fso.GetFolder("D:\Rami Chehab\University Degrees & Courses\PhD in Labour Economics\Data\Data 2016\UNCTAD\1\nOT DONE COUNTRIES\")
For Each file In fldr.Files
'Open the file
Set wb = Workbooks.Open(file.Path)
'## You will need to modify this line to refer to the correct
' module name and macro name:
Application.Run "PERSONAL.XLSB!Ramroum"
Cells.Select
Range("F7").Activate
Application.CutCopyMode = False
Selection.Copy
Workbooks.Add
ActiveSheet.Paste
Application.CutCopyMode = False
' The problem here it is only saving the folder as name 1 and not changing for example for 1 then in the other loop to 2, 3 and so on and so forth
' I think I need your help here in my code
ChDir _
"D:\Rami Chehab\University Degrees & Courses\PhD in Labour Economics\Data\Data 2016\UNCTAD\Okay"
ActiveWorkbook.SaveAs Filename:= _
"D:\Rami Chehab\University Degrees & Courses\PhD in Labour Economics\Data\Data 2016\UNCTAD\Okay\" & CStr(i) & ".xlsx" _
, FileFormat:=xlOpenXMLWorkbook, CreateBackup:=False
ActiveWindow.Close
i = i + 1
'Close the file (it was saved in Macro6 already)
wb.Close SaveChanges:=False
Next
Set file = Nothing
Set fldr = Nothing
Set fso = Nothing
End Sub

Use VBA to Grab Only Part of a Filename/Filepath

I'm not sure how to tackle this issue. I've done quite a bit of research, but most of the answers I find are a little different than what I need.
What I'm trying to accomplish is this:
Open up an existing workbook manually (wbAI),
Start macro,
Use msoFileDialogOpen to find and open a file (call this wb2),
Store part of wb2's file name (there is a date in the file name) as a variable or string. (I'm not sure which is better for this purpose. Maybe I don't need to store it all...),
Paste part of wb2's filename (the date) in a certain cell in wb1,
Copy the necessary data from wb2,
Paste the data in wb1,
Format the data,
Use a VLOOKUP on the pasted data,
Close wb2 without saving
End the macro.
My macro can do every step listed above except for numbers four and five. On one hand, I'm wondering how I need to pursue this, and on the other hand, I'm wondering where this would fit inside my current code.
To give you an example of what I'm talking about: let's say that in step three I open up a workbook that's named "01.31.13 Group Names." And the file path is from a Sharepoint site so it looks like this:
"https://company.com/team/teamone/_layouts/xlviewer.aspx?01.31.13%20Group%20Names%20.xlsm&Source=https......."
How can I pick out only the date in the filename/filepath?
Here's the beginning of my code:
Sub Test()
Dim lastRow As Long, i As Long
Dim ws As Worksheet
Dim wbSource As Workbook
Dim wbAI As Workbook
Dim vrtSelectedItem As Variant
Set wbAI = ActiveWorkbook
Application.ScreenUpdating = False
With Application.FileDialog(msoFileDialogOpen)
.InitialFileName = https://company.com/team/teamone & "\"
.AllowMultiSelect = False
.Show
' ****** Is this where the new code could be inserted? *******
For Each vrtSelectedItem In .SelectedItems
Set wbSource = Workbooks.Open(vrtSelectedItem)
Next
End With
' Check if the first cell contains data. If not then close file
If Range("Profile!H9") = "" Then
ActiveWorkbook.Close savechanges:=False
ActiveWorkbook.Saved = False
Any suggestions are welcome! Thank you for your time!
Edit: This is how my code looks after Philip's suggestion:
Sub Test()
Dim lastRow As Long, i As Long
Dim ws As Worksheet
Dim wbSource As Workbook
Dim wbAI As Workbook
Dim vrtSelectedItem As Variant
Set wbAI = ActiveWorkbook
Application.ScreenUpdating = False
With Application.FileDialog(msoFileDialogOpen)
.InitialFileName = https://company.com/team/teamone & "\"
.AllowMultiSelect = False
.Show
For Each vrtSelectedItem In .SelectedItems
Set wbSource = Workbooks.Open(vrtSelectedItem)
Next
End With
dateVar = Left(wbSource.Name, 8) '<~~~~ New code
' Check if the first cell contains data. If not then close file
If Range("Profile!H9") = "" Then
ActiveWorkbook.Close savechanges:=False
ActiveWorkbook.Saved = False
Else
Sheets("Profile").Activate
Range("H9:I" & Cells(Rows.Count, "H").End(xlUp).Row).Select
Selection.Copy
Windows("wbName").Activate
Sheets("Sheet1").Activate
Range("A2").Select
Selection.PasteSpecial Paste:=xlPasteValues, Operation:=xlNone, SkipBlanks _
:=False, Transpose:=False
Range("E1").Value = dateVar '<~~~ New code
from the filename you would use the LEFT FUNCTION to return the LEFT 8 chars of the date:
dateVar=left(wbSource.name, 8)
then you can put that in your cell:
rangeVar.value=dateVar
hope that gets you going
Philip