iT邦幫忙

第 12 屆 iT 邦幫忙鐵人賽

DAY 28
1
Modern Web

打net core肉飯系列 第 28

[2020鐵人賽] Day28 - 用CsvHelper讀寫csv檔案

公司最近有個需求要處理csv檔案,必須要將資料庫資料轉成csv匯出,而且希望每個資料都有雙引號,並以逗號分隔,同時也希望能讀取csv檔案,並把資料更新置資料庫中。Nuget上有很多元件可以做到,但用來用去還是推薦CsvHelper,在Nuget上下載量有高人氣,足以證明其輕巧好用。

前置準備
如果是使用.net Framework則不需要安裝編碼套件,若是使用.net core架構,必須先安裝編碼套件,若直接使用會發生如下exception,以Big5為例

ArgumentException: 'Big5' is not a supported encoding name. For information on defining a custom encoding, see the documentation for the Encoding.RegisterProvider method.

故在Nuget上安裝System.Text.Encoding.CodePages
https://ithelp.ithome.com.tw/upload/images/20201013/20111766EL8IKsAooh.png
安裝完成需註冊,放在程式的第一行

Encoding.RegisterProvider(CodePagesEncodingProvider.Instance);

接著安裝CsvHelper,同樣也是在Nuget上下載
https://ithelp.ithome.com.tw/upload/images/20201013/20111766nKu17Aqpif.png

建立模型要接資料

public class TestModel
    {
        public int Id { get; set; }
        public string Name { get; set; }
        public int Age { get; set; }
    }

將資料匯出成csv檔案

Encoding.RegisterProvider(CodePagesEncodingProvider.Instance);
var ms = new MemoryStream();
var list = GetTestList(); //去資料庫取得list資料
using (TextWriter writer = new StreamWriter(ms, System.Text.Encoding.UTF8))
            {
                var csv = new CsvHelper.CsvWriter(writer);
                csv.Configuration.QuoteAllFields = true;//雙引號隔開,預設是沒有雙引號
                csv.WriteRecords(list);
            }
            byte[] bytes = ms.ToArray();

產出csv結果
"Id","Name","Age" <-換行
"1","Scott","30"<-換行

接著把結果的這個檔案再丟進去讀取看看

讀取csv檔案

Encoding.RegisterProvider(CodePagesEncodingProvider.Instance);
//file為前端丟過來的檔案,為csv檔
using (var ms = new MemoryStream(file))
                {
                    //可使用big5,但.net core需安裝System.Text.Encoding.CodePages套件
                    using (var reader = new StreamReader(ms, Encoding.GetEncoding("big5")))
                    {
                        using (var csv = new CsvHelper.CsvReader(reader))
                        {
                            ms.Seek(0, SeekOrigin.Begin);
                            var records = csv.GetRecords<TestModel>().ToList();//轉成list,csv第一列欄位需對應class
                            //records為一筆資料的list
                                foreach (TestModel record in records)
                                {
                                    //可針對每筆資料去做事情
                                    record.Id ->1
                                    record.Name -> "Scott"
                                    record.Age -> 30
                                }
                            }
                        }
                    }
                }

參考資料
https://www.cnblogs.com/artech/p/encoding-registeration-4-net-core.html
https://joshclose.github.io/CsvHelper/


上一篇
[2020鐵人賽] Day27 - 部署與相關設定
下一篇
[2020鐵人賽] Day29 - 切換身分Impersonation
系列文
打net core肉飯30

尚未有邦友留言

立即登入留言