2014年2月12日 星期三

[ASP.NET C#] 把Excel資料匯入資料庫的懶人Code分享 - Microsoft.office.Interop.Excel篇

Reference:http://www.dotblogs.com.tw/shadow/archive/2011/05/02/24045.aspx

[ASP.net WebForm] 把Excel資料匯入資料庫的懶人Code分享 - Microsoft.office.Interop.Excel篇

常常碰到這種需求,為了避免自己每次寫Code都要東翻西找Sample,乾脆丟上來當備份
此外,也為了方便網路上的大大們Copy Paste方便,小弟已經順便標示要複製程式碼的起始結束位置

在歡樂的貼程式前
請先注意公司的測試機電腦是否有先做設定

簡單講一下程式碼流程:1.上傳Excel檔。2. ASP.net讀Excel資料,然後Insert into Table。3.把上傳的Excel檔宰掉,避免硬碟空間不夠。
using System;
using System.Collections.Generic;
using System.Web;
 
 
 
/***Copy Start***/
//引用Microsoft Excel相關參考
using Microsoft.Office.Interop;
using Microsoft.Office.Interop.Excel;
//移機時記得Bin底下的Microsoft.Office.Interop.Excel.dll和office.dll等,Excel相關dll也要Copy過去
/***Copy End***/
 
public class ExcelImport :System.Web.UI.Page
{
    /***Copy Start***/
    //畫面上要先擺一個FileUpload控制項
 
    /*** Excel Interop reference ***/
    Microsoft.Office.Interop.Excel.Application xlApp = null;
    Workbook wb = null;
    Worksheet ws = null;
    Range aRange = null;
    //*******************************/
 
    //要上傳Excel檔的Server端 檔案總管目錄
    string upload_excel_Dir = @"D:\web\myWeb\";
 
 
    #region 匯入EXCEL
    //按鈕Click事件
    protected void lbtOK_Click(object sender, EventArgs e)
    {
        string excel_filePath = "";
        try
        {
            excel_filePath = SaveFileAndReturnPath();//先上傳EXCEL檔案給Server
 
            if (this.xlApp == null)
            {
                this.xlApp = new Microsoft.Office.Interop.Excel.Application();
            }
            //打開Server上的Excel檔案
            this.xlApp.Workbooks.Open(excel_filePath, Type.Missing, Type.Missing, Type.Missing, Type.Missing, Type.Missing, Type.Missing, Type.Missing, Type.Missing, Type.Missing, Type.Missing, Type.Missing, Type.Missing, Type.Missing, Type.Missing);
            this.wb = xlApp.Workbooks[1];//第一個Workbook
            this.wb.Save();
 
            //從第一個Worksheet讀資料
            SaveOrInsertSheet(excel_filePath, (Worksheet)xlApp.Worksheets[1]);
 
 
             
            ClientScript.RegisterClientScriptBlock(typeof(System.Web.UI.Page), "匯入完成""alert('匯入完成');"true);
             
        }
        catch (Exception ex)
        {
            throw ex;
        }
        finally
        {
            xlApp.Workbooks.Close();
            xlApp.Quit();
            try
            {
                //刪除 Windows工作管理員中的Excel.exe 處理緒.
                System.Runtime.InteropServices.Marshal.ReleaseComObject(this.xlApp);
                System.Runtime.InteropServices.Marshal.ReleaseComObject(this.ws);
                System.Runtime.InteropServices.Marshal.ReleaseComObject(this.aRange);
            }
            catch { }
            this.xlApp = null;
            this.wb = null;
            this.ws = null;
            this.aRange = null;
 
 
            //是否刪除Server上的Excel檔
            bool isDeleteFileFromServer = true;
            if (isDeleteFileFromServer)
            {
                System.IO.File.Delete(excel_filePath);
            }
 
 
            GC.Collect();
        }
    }
    #endregion
 
    #region 儲存EXCEL檔案給Server
    private string SaveFileAndReturnPath()
    {
        string return_file_path = "";//上傳的Excel檔在Server上的位置
        if (FileUpload1.FileName != "")
        {
            return_file_path = System.IO.Path.Combine(this.upload_excel_Dir, Guid.NewGuid().ToString() + ".xls");
 
            FileUpload1.SaveAs(return_file_path);
        }
        return return_file_path;
    }
    #endregion
 
    #region 把Excel資料Insert into Table
    private void SaveOrInsertSheet(string excel_filename,Worksheet ws)
    {
 
        //要開始讀取的起始列(微軟Worksheet是從1開始算)
        int rowIndex = 1;
 
        //取得一列的範圍
        this.aRange = ws.get_Range("A" + rowIndex.ToString(), "C" + rowIndex.ToString());
 
        //判斷Row範圍裡第1格有值的話,迴圈就往下跑
        while (((object[,])this.aRange.Value2)[1, 1] != null)//用this.aRange.Cells[1, 1]來取值的方式似乎會造成無窮迴圈?
        {
            //範圍裡第1格的值
            string cell1 = ((object[,])this.aRange.Value2)[1, 1] != null ? ((object[,])this.aRange.Value2)[1, 1].ToString() : "";
 
            //範圍裡第2格的值
            string cell2 = ((object[,])this.aRange.Value2)[1, 2] != null ? ((object[,])this.aRange.Value2)[1, 2].ToString() : "";
 
            //範圍裡第3格的值
            string cell3 = ((object[,])this.aRange.Value2)[1, 3] != null ? ((object[,])this.aRange.Value2)[1, 3].ToString() : "";
             
            //再對各Cell處理完商業邏輯後,Insert into Table...(略
 
 
 
 
 
 
            //往下抓一列Excel範圍
            rowIndex++;
            this.aRange = ws.get_Range("A" + rowIndex.ToString(), "C" + rowIndex.ToString());
        }
 
 
    }
    #endregion
 
    /***Copy End***/
}
2011.5.21 追記

本文介紹的方法,程式可以從Excel把資料抓出來,做商業邏輯處理後再Insert into Table

1 則留言:

  1. William哥 你好
    謝謝你的文章 讓我增進不少

    遇到了點小麻煩 想拜託你 指導一下
    我以這邊文章為基礎 在家裡打了一個aspx的 excel 上傳到 sql 的程式
    在家裡執行成功 資料也有進去 sql
    但是帶到公司 發布上server 卻執行失敗
    出現 "例外詳細資訊: System.NullReferenceException: 並未將物件參考設定為物件的執行個體。"
    我有按照 "讀寫Excel的相關設定" 做設定
    我的excel 有成功上傳到 server上指定的資料夾
    然後就出現 System.NullReferenceException 錯誤了

    回覆刪除