ASP.NET控制元件FileUpload實現Excel檔案內容上傳到資料庫
阿新 • • 發佈:2019-01-22
實現思路:Excel的內容並不可以直接上傳到資料庫,所以先將Excel內容讀取出來轉化為DataSet,然後可以得到DataTable,遍歷每一行,存到資料庫裡就好了。
前臺只放了兩個控制元件:
<asp:Button ID="btnUpload" class="btnStyle" runat="server" Text="上傳" OnClick="btnUpload_Click" />
<asp:FileUpload ID="FileUpload1" runat="server" />
後臺如下:
namespace *********不顯示了無關緊要************
{
public partial class UploadExcelFile : System.Web.UI.Page
{
UploadExcelFileBiz uploadExcelFileBiz = new UploadExcelFileBiz();
protected void Page_Load(object sender, EventArgs e)
{
}
/// <summary>
/// 上傳至資料庫
/// </summary>
/// <param name="sender"></param>
/// <param name="e"></param>
protected void btnUpload_Click(object sender, EventArgs e)
{
//bool style = false;
string road = "";
#region 檔案上傳
try
{
//全名
string excelFile = this.FileUpload1.PostedFile.FileName;
//獲取檔名(不包括副檔名)
string fileName = Path.GetFileNameWithoutExtension(FileUpload1.PostedFile.FileName);
//副檔名
string extentionName = excelFile.Substring(excelFile.LastIndexOf(".") + 1);
if (fileName == "" || fileName == null)
{
Response.Write("<script>alert('請先選擇Excel檔案!')</script>");
return;
}
if (extentionName != "xls" && extentionName != "xlsx")
{
Response.Write("<script>alert('您上傳的不是Excel檔案!')</script>");
return;
}
//瀏覽器安全性限制 無法直接獲取客戶端檔案的真實路徑,將檔案上傳到伺服器端 然後獲取檔案源路徑
#region 設定上傳路徑將檔案儲存到伺服器
string dateTime = DateTime.Now.Date.ToString("yyyyMMdd");
string time = DateTime.Now.ToShortTimeString().Replace(":", "");
string newFileName = dateTime + time + DateTime.Now.Millisecond.ToString() + ".xls"; ;
//Annex是自己建立的資料夾 位置隨意 合理即可
road = Server.MapPath("..\\..\\Annex") + "\\" + newFileName;
this.FileUpload1.PostedFile.SaveAs(road);
//Response.Write("<script>alert('已經上傳到伺服器資料夾')</script>");
#endregion
}
catch
{
Response.Write("<script>alert('資料上傳失敗,請重新匯入')</script>");
return;
}
#endregion
#region 資料匯入
try
{
#region 讀取成DataSet 然後轉化為Table
string strConn = "Provider=Microsoft.Jet.OLEDB.4.0;Data Source='" + road + "';" +
"Extended Properties='Excel 8.0;IMEX=1'";
DataSet dsMin = new DataSet();
OleDbDataAdapter oada = new OleDbDataAdapter("select * from [模板(5分鐘)$]", strConn);
oada.Fill(dsMin);
DataSet dsHour = new DataSet();
OleDbDataAdapter oada2 = new OleDbDataAdapter("select * from [模板(小時)$]", strConn);
oada2.Fill(dsHour);
DataTable dtMin = dsMin.Tables[0];
DataRow[] dr = dtMin.Select();
int rowsNum = dtMin.Rows.Count;
string a, b, c, d, f, g, h;
//遍歷獲取的Excel內容 dr[行][列] 下標索引從0開始
for (int i = 2; i < rowsNum; i++)
{
//序號
a = dr[i][0].ToString();
//時間
b = dr[i][1].ToString();
//本人上傳的Excel第三列有空格,所以輪空
c = dr[i][3].ToString();
d = dr[i][4].ToString();
f = dr[i][5].ToString();
g = dr[i][6].ToString();
h = dr[i][7].ToString();
//插入資料庫 Add是自定義的方法
uploadExcelFileBiz.Add(Convert.ToDateTime(b), c, d, f, g, h);
}
#region SqlBulkCopy批量寫入資料庫
DataTable dtHour = dsHour.Tables[0];
dtHour .Columns[0].ColumnName = "UploadTime";
dtHour.Columns[1].ColumnName = "Data1";
dtHour.Columns[2].ColumnName = "Data2";
dtHour.Columns[3].ColumnName = "Data3";
dtHour.Columns[4].ColumnName = "Data4";
dtHour.Columns[5].ColumnName = "Data5";
uploadExcelFileBiz.WriteIntoDataBase(dtHour);
#endregion
#endregion
}
catch
{
Response.Write("<script>alert('匯入資料失敗!')</script>");
return;
}
#endregion
}
}
}
附上SqlBulkCopy批量寫入資料庫的方法如下:
DAL層:
/// <summary>
/// 利用SqlBulkCopy批量寫入資料庫
/// </summary>
/// <param name="dt"></param>
public void WriteIntoDataBase(DataTable dt)
{
SqlConnection myConn = new SqlConnection(System.Configuration.ConfigurationManager.ConnectionStrings["dbBaseDatabase"].ConnectionString);
myConn.Open();
SqlBulkCopy bulkCopy = new SqlBulkCopy(myConn);
bulkCopy.BatchSize = 10000;
bulkCopy.BulkCopyTimeout = 60;
bulkCopy.DestinationTableName = "T_Sys_UploadTest";
for (int i = 0; i < dt.Columns.Count; i++)
{
string columnName = dt.Columns[i].ColumnName;
bulkCopy.ColumnMappings.Add(columnName, columnName);
}
bulkCopy.WriteToServer(dt);
//myConn.Close();
myConn.Dispose();
}
注意事項:
dataTable的表頭得和所要插入的資料庫表中的欄位名稱一一對應,注意重新命名:如:dataTable.Columns[0].ColumnName = "內容";
備註:
SqlBulkCopy這種批量寫入方式,可以大大的節約資料庫匯入資料的時間,因為字串的拼接的方式寫入資料庫需要不停的開啟和關閉連線。
上述內容則提供了這兩種方法,方便對比
-----------------------分割線----2017.06.26更新-------附上UploadExcelFileBiz.cs--------------------
using ApplyForNetwork.DAL.ApplyForNetwork.Sys;
using System;
using System.Collections.Generic;
using System.Data;
using System.Linq;
using System.Text;
namespace ApplyForNetwork.BLL.ApplyForNetwork.Sys
{
public class UploadExcelFileBiz
{
UploadExcelFileDA uploadExcelFileDA = new UploadExcelFileDA();
public UploadExcelFileBiz()
{
}
/// <summary>
/// 利用SqlBulkCopy批量寫入資料庫
/// </summary>
/// <param name="dt"></param>
public void WriteIntoDataBase(DataTable dt,string tableName)
{
uploadExcelFileDA.WriteIntoDataBase(dt, tableName);
}
/// <summary>
/// 建立臨時表
/// </summary>
/// <returns></returns>
public DataTable tmpTable()
{
DataTable dt = new DataTable();
dt.Columns.Add("ID", typeof(int));
dt.Columns.Add("PortId",typeof(string));
dt.Columns.Add("Tstamp", typeof(DateTime));
dt.Columns.Add("ZAD_DATA1", typeof(Decimal));
dt.Columns.Add("MinusData1", typeof(Decimal));
dt.Columns.Add("ZAD_DATA3", typeof(Decimal));
dt.Columns.Add("MinusData3", typeof(Decimal));
dt.Columns.Add("ZAD_DATA4", typeof(Decimal));
dt.Columns.Add("MinusData4", typeof(Decimal));
dt.Columns.Add("ZAD_DATA6", typeof(Decimal));
dt.Columns.Add("MinusData6", typeof(Decimal));
dt.Columns.Add("ZAD_DATA9", typeof(Decimal));
dt.Columns.Add("MinusData9", typeof(Decimal));
dt.Columns.Add("CheckBatch", typeof(string));
return dt;
}
}
}