How to convert multiple xls files to csv using powershell?

Tag: excel , powershell , csv , xls Author: aeobea Date: 2011-05-03

I'm trying to convert multiple Excel files (xls) to csv using the following powershell script:

$excel = new-object -ComObject "Excel.Application"
$excel.Visible =$false
foreach ($file in get-childitem $src_dir) {
    $wb = $excel.Workbooks.Open($file.FullName)
    $wb.SaveAs($dst_dir + $file.Name + ".csv", 6)# 6 -> csv

In principle this works e.g. I get csv files. However, for a few files (varying per run) I get an exception:

Exception calling "SaveAs" with "2" argument(s): "Microsoft Office Excel cannot access the file 'C:\Users\...\AppData\Local\Temp'. ...

Additionally, I get a message box asking if I want to save the changes to the source xls.

Once I call SaveAs, $wb references the new file. So how do I save or discard the changes to the source file? Why does this happen only for a few files? Are there any other problems with this script?


I divided the input files (ca. 200) arbitrarily (i.e. don't know the size of the groups) into 10 groups and processed each group in its own run. That worked so it is somewhat inconvenient.

thanks in advance

Do you have a look to the tempory file shown in the error, just to see if there are no file remaining. I met a similar problem in a PDF conversion script and old temprary file remaining were at the origin of the trouble.
Unfortunately, the error message only names the Temp directory. I monitored the directory during a run and two files (supposably for each converted xls) with random names showed up and vanished.

Other Answer1

Try moving the code to launch and quit excel INSIDE your loop.

Yeah, it's slower that way, but it'll encourage Excel to clean up its temp files between each operation.

It won't be as slow as you think because Windows and COM are smart enough to keep Excel mostly in memory even after you quit for a few seconds so that the next time you create an Excel object it'll happen fast, exactly for situations like this.

Other Answer2

Maybe you can implement a timer to wait a while? Or you have a look inside the direcotry while you script is running and then remove the temp files after each cycle (one xls file conversion).