Killing Excel.EXE on server [duplicate]

Tags: excel asp.net
Question!

Possible Duplicate:
How to properly clean up Excel interop objects in C#

Suppose a ASP.NET web application generates automated Excel Reports on the server. How do we kill a server-side Excel.EXE once the processing is over. I am raising this purposely, because I believe that the Garbage Collecter does not clean the Excel executable even after the Excel file is closed.

Any pointers would be helpful?



Answers

I've had more time to think about this answer, and would now recommend using an XML approach with the Open XML Office spreadsheet format.

Heres some good links to get started on building a office document with code. http://msdn.microsoft.com/en-us/magazine/cc163478.aspx http://msdn.microsoft.com/en-us/library/bb735940(office.12).aspx

Just use SSIS on SQL Server. It provides the ability to export to Excel. Don't run office on the server. Alteranatively waste money on aspose or spreadsheetgear.

GC does work your just not using it properly follow this pattern...

   private void killExcel()
        {
          xlApp.Quit();
          Marshal.ReleaseCOMObject(xlApp);
          if(xlApp != null)
          {
            xlApp = null;
          }
          GC.WaitForPendingFinalizers();
          GC.Collect();
          GC.WaitForPendingFinalizers();
          GC.Collect();
        }

get your Excel operational class to implement IDisposable, and then stick killExcel() in the Dispose method.

UPDATE: Also note that sometimes dev will still see Excel.exe running in task manager. Before assuming the above code isn't working, check that the process that is running the code is also closed. In the case of a VSTO or COM addin, check that Word/powerpoint/other excel instance is also closed as there is still a GC root back to the launching process. Once that is closed the Excel.exe process will close.



The best approach is to use a purpose built library such as the one from Aspose to generate the spreadsheets or populate templates. The next best approach is to use the xml formats for office if practical for your needs. A lightweight approach that is sometimes suitable is to create an HTML file with one table in it and name it with an .xls extension. Excel will happily read that, but it is very limited in what it can do.

Those are the options I've used (but not much). There's also a thing called Microsoft Office Sharepoint Server, but I've no idea how much it really lets you do.

That said, your problem is happening because when you invoke the regular Excel libraries, you're actually spinning up Excel completely independently of .Net and actually just working with a proxy library to talk to it. This is pretty much the same kind of thing you'd have with WCF and a service. You wouldn't expect the service to die just because the client application was done using it. Worse, Excel is an unmanaged resource and will not be disposed/ finalized/ garbage collected at all. The .Net Runtime doesn't know about Excel, it just knows about those proxies. Application.quit is what you need and also you may need to explicitly release the com objects that are created.

By : Jim L


You need safely dispose all COM interop objects after you end your work. By "all" I mean absolutely all: collections property values and so on. I've created stack object and pushed objects during their setup:

Stack<object> comObjectsToRelease = new Stack<object>();
...
Log("Creating VBProject object.");
VBProject vbProject = workbook.VBProject;
comObjectsToRelease.Push(vbProject);
...
finally
{
    if(excel != null)
    {
        Log("Quiting Excel.");
        excel.Quit();
        excel = null;
    }
    while (comObjectsToRelease.Count > 0)
    {
        Log("Releasing {0} COM object.", comObjectsToRelease.GetType().Name);
        Marshal.FinalReleaseComObject(comObjectsToRelease.Pop());
    }               
    Log("Invoking garbage collection.");
    GC.Collect();
}

If Excel is still there you have to kill it manually.



This video can help you solving your question :)
By: admin