1. 程式人生 > >【C#MVC】使用ajaxFileUpload匯入Excel,並顯示在Grid中

【C#MVC】使用ajaxFileUpload匯入Excel,並顯示在Grid中

學習瞭如何使用ajaxFileUpload(無重新整理上傳)匯入Excel檔案,並在頁面中顯示出來。C#,asp和MVC操作形似,這裡重點說MVC,asp只貼出來程式碼。
準備:在頁面引入js檔案。
Step1:(ajaxFileUpload是一個開源專案,有很多版本。原理相似,建立隱藏表單和iframe,使用js提交)寫出JS
options引數說明:
1、url           上傳處理程式地址。  
2,fileElementId      需要上傳的檔案域的ID,即的ID。
3,secureuri        是否啟用安全提交,預設為false。
4,dataType        伺服器返回的資料型別。可以為xml,script,json,html。如果不填寫,jQuery會自動判斷。
5,success        提交成功後自動執行的處理函式,引數data就是伺服器返回的資料。
6,error          提交失敗自動執行的處理函式。
7,data           自定義引數。這個東西比較有用,當有資料是與上傳的圖片相關的時候,這個東西就要用到了。
8, type           當要提交自定義引數時,這個引數要設定成post

錯誤提示:
1,SyntaxError: missing ; before statement錯誤
  如果出現這個錯誤就需要檢查url路徑是否可以訪問
2,SyntaxError: syntax error錯誤
  如果出現這個錯誤就需要檢查處理提交操作的伺服器後臺處理程式是否存在語法錯誤
3,SyntaxError: invalid property id錯誤
  如果出現這個錯誤就需要檢查文字域屬性ID是否存在
4,SyntaxError: missing } in XML expression錯誤
  如果出現這個錯誤就需要檢查檔案name是否一致或不存在
5,其它自定義錯誤
  大家可使用變數$error直接列印的方法檢查各引數是否正確,比起上面這些無效的錯誤提示還是方便很多。

<script language="javascript" type="text/javascript">    
    function ajaxFileUpload() {
        $.ajaxFileUpload({
            url: '/TestController/TestImportExcel', //用於檔案上傳的伺服器端請求地址
            secureuri: false, //是否需要安全協議,一般設定為false
            fileElementId: 'fuExcelUpload', //檔案上傳域的ID
            dataType: 'json'
, //返回值型別 一般設定為json success: function (data, status) { LoadGrid(); $("#tbShipmentList").datagrid('loadData', data); }, error: function (data, status, e)//伺服器響應失敗處理函式 { alert("Error:Please contact administrator."); } }); } function LoadGrid() { $("#tbShipmentList").datagrid({ striped: true, loadMsg: "Loading", rownumbers: true, idField: "SerialNumber", checkOnSelect: false, selectOnCheck: false, singleSelect: true, frozenColumns: [[ { title: 'Shipment No.', field: 'ShipmentNumber', formatter: function (value, row, index) { if (row.Result == 0) { return '<font color="green">' + value + '</font>';; } else { return '<font color="red">' + value + '</font>';; } } } ]], columns: [[ { title: 'Origin', field: 'Origin' }, { title: 'Destination', field: 'Destination' }, { title: 'Pieces', field: 'Pieces' }, { title: 'Weight', field: 'ChargeableWeight(KG)' }, { title: 'ImportResult', field: 'ResutlMsg' } ]] }); }
</script>

Step2:在後臺接受,並做處理。主要是建立一個Excel檔案到伺服器端,然後使用Excel的資料庫引擎,進行查詢,最後返回一個DateTable,然後將DateTable轉化為Grid可識別的Json字串即可。

public string TestImport()
        {           
            HttpFileCollectionBase files = Request.Files; //接受上傳的檔案
            if (files.Count > 0)
            {
                string fileName = "Test" + DateTime.Now.ToString("yyyyMMddhhmmssms") + ".xls";
                string filePath = System.Configuration.ConfigurationManager.AppSettings["ExcelUpload"].ToString();
                if (files[0].ContentLength == 0)
                {
                    throw new Exception("No file upload!");
                }
                files[0].SaveAs(filePath + fileName);// 儲存上傳的檔案到伺服器端
                DataTable dt = OleDBHelper.DoOleSql(filePath + fileName, fileName); 
                // 使用工具類查詢出Excel的資料
                dt.Columns.Add("ResutlMsg");
                dt.Columns.Add("Result");
                for (int i = 0; i < dt.Rows.Count; i++)
                {
                    ExcelDataValidation(dt.Rows[i]);
                }
                string res = JsonHelper.ToGridJson(dt, dt.Rows.Count);//轉化為Json
                Session["GridList"] = res;
                Response.Write(res);
            }
            return "";           
        }

其中重要的工具類:OleDBHelper:

 public static class OleDBHelper
    {
        public static DataTable DoOleSql(string database, string fileName)
        {
            string strConn = null;
            int Num = fileName.LastIndexOf('.');
            string fileExt = "";
            if (Num > 0)
            {
                fileExt = fileName.Substring(Num).ToLower();
            }
            if (fileExt == ".xlsx") //excel2007的檔案            
            {
                strConn = "Provider=Microsoft.Ace.OleDb.12.0;;Data Source=\"" + database + "\";Extended Properties=\"Excel 12.0;HDR=YES;IMEX=1;\"";
            }
            if (fileExt == ".xls")//excel2003的檔案            
            {
                strConn = "Provider=Microsoft.Jet.OleDb.4.0;Data Source=\"" + database + "\";Extended Properties=\"Excel 8.0;HDR=YES;IMEX=1;\"";
            }


            OleDbConnection conn;
            DataSet ds = new DataSet();
            conn = new OleDbConnection(strConn);
            conn.Open();
            //返回Excel的架構,包括各個sheet表的名稱,型別,建立時間和修改時間等
            DataTable dtSheetName = conn.GetOleDbSchemaTable(OleDbSchemaGuid.Tables, new object[] { null, null, null, "Table" });
            //包含excel中表名的字串陣列
            string[] strTableNames = new string[dtSheetName.Rows.Count];
            string[] strTables = new string[dtSheetName.Rows.Count];
            int k;
            string temp;
            string[] ids = new string[dtSheetName.Rows.Count];
            for (k = 0; k < dtSheetName.Rows.Count; k++)
            {
                temp = dtSheetName.Rows[k]["TABLE_NAME"].ToString();
                strTables[k] = temp.Trim('$');
                strTableNames[k] = temp;
            }

            OleDbDataAdapter myCommand = null;

            DataTable dt = new DataTable();
            //從指定的表明查詢資料,可先把所有表明列出來供使用者選擇
            string strExcel = "select * from [" + strTableNames[0] + "]";
            myCommand = new OleDbDataAdapter(strExcel, strConn);
            myCommand.Fill(dt);
            conn.Close();
            dt.TableName = strTables[0];
            return dt;

        }
    }

最後將在Asp中如何使用ajaxFileUpload,貼出來:
Part 1:(頁面部分,與MVC中相似,唯一不同的是MVC請求Controller資料,而Asp請求ashx頁面。)

<script language="javascript" type="text/javascript">
    if(typeof JSON == 'undefined'){$('head').append($("<script type='text/javascript' src='../../JS/easyui1.3.2/json2.js'>"));}
      function ajaxFileUpload() {
            $.ajaxFileUpload({
                url: 'DataFile/UploadExcel.ashx', //用於檔案上傳的伺服器端請求地址
                secureuri: false, //是否需要安全協議,一般設定為false
                fileElementId: 'fuExcelUpload', //檔案上傳域的ID
                dataType: 'json', //返回值型別 一般設定為json
                success:function(data,status){                     
                    LoadGrid();
                    $("#tbShipmentList").datagrid('loadData',data);                                    
                },
                error: function (data, status, e)//伺服器響應失敗處理函式
                {                
                    alert(data.responseText);
                }
            });        
        }  
       function LoadGrid(){                      
            $("#tbShipmentList").datagrid({                
                striped:true,                
                loadMsg:"Loading",
                rownumbers:true,                
                idField:"SerialNumber",
                checkOnSelect: false, 
                selectOnCheck: false,
                singleSelect:true,
                frozenColumns:[[ 
                    {checkbox:true },                 
                    {title:'Shipment No.',field:'ShipmentNumber',formatter:
                        function(value, row, index){    
                            if(row.Result == 0){
                                return '<font color="green">' + value + '</font>';;
                            }else{
                                return '<font color="red">' + value + '</font>';;
                            }                                              

                    }}
                ]],
                columns:[[                                                                              
                    {title:'Consignee Email',field:'ConsigneeEmail'},
                    {title:'Consignee Name',field:'ConsigneeName'},
                    {title:'Consignee Address',field:'ConsigneeAddress'},                    
                    {title:'Consignee City',field:'ConsigneeCity'},
                    {title:'Consignee Zip',field:'ConsigneeZip'},
                    {title:'Consignee Contact',field:'ConsigneeContact'},
                    {title:'Consignee Tel No.',field:'ConsigneeTel'}
                ]]
            });
        }
  </script>    

Part 2: 在ashx如同Controller中一樣處理Excel,並查詢。

public class UploadExcel : IHttpHandler, System.Web.SessionState.IReadOnlySessionState
{

    public void ProcessRequest (HttpContext context)
    {
        try 
        {
            context.Response.ContentType = "text/plain";
            HttpFileCollection files = context.Request.Files;
            string branchCode = context.Session["BranchCode"].ToString(); 
            if (files.Count > 0)
            {
                string fileName = "Shipment" + DateTime.Now.ToString("yyyyMMddhhmmssms") + ".xls";
                string filePath = System.Configuration.ConfigurationManager.AppSettings["SendMailTmp"].ToString();
                if (Directory.Exists(filePath) == false)//如果不存在就建立file資料夾
                {
                    Directory.CreateDirectory(filePath);
                } 
                if (files[0].ContentLength == 0)
                {
                    throw new Exception("No file upload!");
                }
                files[0].SaveAs(filePath + fileName);
                DataTable dt = DoOleSql(filePath + fileName, fileName);


                string res = JsonHelper.ToGridJson(dt, dt.Rows.Count);
                context.Session["GridList"] = res;
                context.Response.Write(res);
               Directory.Delete(filePath,true); 
            } 
        }
        catch(Exception ex)
        {
            throw ex;
        }   
    }



    public System.Data.DataTable DoOleSql(string database, string fileName)
    {
        string strConn = null;
        int Num = fileName.LastIndexOf('.');
        string fileExt = "";
        if (Num > 0)
        {
            fileExt = fileName.Substring(Num).ToLower();
        }
        if (fileExt == ".xlsx") //excel2007的檔案            
        {
            strConn = "Provider=Microsoft.Ace.OleDb.12.0;;Data Source=\"" + database + "\";Extended Properties=\"Excel 12.0;HDR=YES;IMEX=1;\"";
        }
        if (fileExt == ".xls")//excel2003的檔案            
        {
            strConn = "Provider=Microsoft.Jet.OleDb.4.0;Data Source=\"" + database + "\";Extended Properties=\"Excel 8.0;HDR=YES;IMEX=1;\"";
        }
        OleDbConnection conn;
        DataSet ds = new DataSet();
        conn = new OleDbConnection(strConn);
        conn.Open();
        //返回Excel的架構,包括各個sheet表的名稱,型別,建立時間和修改時間等
        DataTable dtSheetName = conn.GetOleDbSchemaTable(OleDbSchemaGuid.Tables, new object[] { null, null, null, "Table" });
        //包含excel中表名的字串陣列
        string[] strTableNames = new string[dtSheetName.Rows.Count];
        string[] strTables = new string[dtSheetName.Rows.Count];
        int k;
        string temp;
        string[] ids = new string[dtSheetName.Rows.Count];
        for (k = 0; k < dtSheetName.Rows.Count; k++)
        {
            temp = dtSheetName.Rows[k]["TABLE_NAME"].ToString();
            strTables[k] = temp.Trim('$');
            strTableNames[k] = temp;
        }

        OleDbDataAdapter myCommand = null;

        DataTable dt = new DataTable();
        //從指定的表明查詢資料,可先把所有表明列出來供使用者選擇
        string strExcel = "select * from [" + strTableNames[0] + "]";
        myCommand = new OleDbDataAdapter(strExcel, strConn);
        myCommand.Fill(dt);
        conn.Close();
        dt.TableName = strTables[0];
        return dt;

    }
    public bool IsReusable {
        get {
            return false;
        }
    }

}