[Osaka/Yokohama] Looking for infrastructure/server side engineers!

[Osaka/Yokohama] Looking for infrastructure/server side engineers!

[Deployed by over 500 companies] AWS construction, operation, maintenance, and monitoring services

[Deployed by over 500 companies] AWS construction, operation, maintenance, and monitoring services

[Successor to CentOS] AlmaLinux OS server construction/migration service

[Successor to CentOS] AlmaLinux OS server construction/migration service

[For WordPress only] Cloud server “Web Speed”

[For WordPress only] Cloud server “Web Speed”

[Cheap] Website security automatic diagnosis “Quick Scanner”

[Cheap] Website security automatic diagnosis “Quick Scanner”

[Reservation system development] EDISONE customization development service

[Reservation system development] EDISONE customization development service

[Registration of 100 URLs is 0 yen] Website monitoring service “Appmill”

[Registration of 100 URLs is 0 yen] Website monitoring service “Appmill”

[Compatible with over 200 countries] Global eSIM “Beyond SIM”

[Compatible with over 200 countries] Global eSIM “Beyond SIM”

[If you are traveling, business trip, or stationed in China] Chinese SIM service “Choco SIM”

[If you are traveling, business trip, or stationed in China] Chinese SIM service “Choco SIM”

[Global exclusive service] Beyond's MSP in North America and China

[Global exclusive service] Beyond's MSP in North America and China

[YouTube] Beyond official channel “Biyomaru Channel”

[YouTube] Beyond official channel “Biyomaru Channel”

【ASP.NET core 3】Entity Framework Coreを使用してCSVファイルをダウンロードしてみた

こんにちは、システム開発部のながたにです。
今、ASP.NET core を使用した開発をしておりまして、Entity Framework Core 3 を使用しているのですが、その Entity Framework Core で DB から取得したデータを ボタンをクリックすることで CSV ファイルとしてダウンロードできる機能を実装しました。

今回はその実装の方法について、紹介させていただきます。

プロジェクトを作成する

まずは ASP.NET Core 3 MVC のプロジェクトを作成します。

1. Visual Studio 2019 を開きます
2.「新しいプロジェクトの作成」を選択します

3.「ASP.NET Core Web アプリケーション」を選択します

4. プロジェクト名を任意で入力して作成します(今回は CsvDownload としました)

これでプロジェクトが作成されました。

ASP.NET Core 3 で Entity Framework Core 3 を使用できるようにする

公式のドキュメントにチュートリアルがありますので、こちらを参考にしながら、Entity Framework Core 3 を使用できるように設定してください。
あくまで CSV ファイルのダウンロードの実装方法を紹介することが目的ですので、今回は割愛させていただきます。

データを用意する

まずは、CSVファイル をダウンロードするデータを用意する必要があるので、Entity Framework Core 3 を使用してテーブルを作成し、データを挿入していきましょう。

■ テーブルを用意する
今回は Users テーブルを用意します。
カラムは
Id :プライマリーキー
Name:名前
Age:年齢
Height:身長
Weight:体重

にしましょう。

■ User モデルを作成する
次に上記テーブルを作成するため、 User モデルを用意します。
Models フォルダ以下に User.cs を作成します。

作成した User.cs を開いて、下記コードのようにカラムのプロパティを定義しましょう。

namespace CsvDownload.Models
{
    /// <summary>
    /// Users テーブルのモデルクラス
    /// </summary>
    public class User
    {
        public int       Id      { get; set; }  // ID プライマリーキー
        public string    Name    { get; set; }  // 名前
        public int       Age     { get; set; }  // 年齢
        public float     Height  { get; set; }  // 身長
        public float     Weight  { get; set; }  // 体重
    }
}

■ コンテキストファイルを作成する
次に、DB と Model の接続を行うためのコンテキストファイルを用意します。
今回は プロジェクト下にContext.cs を作成しました。

作成した Context.cs に以下のようにコードを記述します。

using CsvDownload.Models;
using Microsoft.EntityFrameworkCore;

namespace CsvDownload
{
    /// <summary>
    /// DB との接続を行うためのコンテキストクラス
    /// </summary>
    public class Context : DbContext
    {
        public Context(DbContextOptions<Context> options) : base(options)
        {

        }

        // モデルをセットする
        public DbSet<User> Users { get; set; }  // プロパティ名がテーブル名になる(この場合だと Users テーブルが作成される)
    }
}

■ 作成したコンテキストファイルをDI コンテナーに追加してEntity Framework Core として使用できるようにする
次に、Startup.cs の ConfigureServices メソッドに 先ほど作成したコンテキストを追加します

services.AddDbContext<Context>(options =>
        options.UseSqlServer("Server=(localdb)\\mssqllocaldb;Database=CsvDownload;Trusted_Connection=True;MultipleActiveResultSets=true"));

※DBの接続文字列(UseSqlServerの部分)は任意で入力してください。特にこだわりがなければ、上記の記述でLocal環境にCsvDownload DBが作成されます。

■ マイグレーションファイルを作成する
これで、準備が整いましたので、次に Users テーブルを作成するためのマイグレーションファイルを作成します。
こちらはコンソールからコマンドを実行するだけで簡単に作成ができます。

[ツール] から [パッケージマネージャーコンソール] を開く

コンソールを開いたら以下のコマンドを実行する

PM> Add-Migration CreateTableUsers

※Add-Migration の後ろはマイグレーション名です。任意で設定してください。

これでMigration フォルダが作成されその中にマイグレーションファイルとマイグレーションのスナップショットファイルが作成されます。

■ マイグレーションを実行する
マイグレーションファイルを作成したときと同様、コンソールでコマンドを実行します。
マイグレーションを実行するコマンドは以下となります。

PM> Update-Database

成功すると DB が作成され Users テーブルが作成されます。
※[表示] ⇒ [SQL Server オブジェクト エクスプローラー] から確認ができます。

■ データを挿入する
これでテーブルが作成されましたので、あとは適当にデータを挿入してください。
※ [SQL Server オブジェクト エクスプローラー]からテーブルを選択して、[データを表示] をクリックすると テーブル内のデータが表示されるので、そこから直接挿入することが可能です。


CSV ダウンロード機能を実装する

お待たせしました... ここからがやっと本題になります。
先ほど挿入したUsers テーブルのデータをCSVダウンロードできるようにしましょう。

■ CsvHelper パッケージをインストールする
まず、CSV形式でダウンロードするために必要な、CsvHelper というパッケージをインストールします
[ツール] ⇒ [NuGet パッケージマネージャー] ⇒ [ソリューションの NuGet パッケージの管理] の順に選択します

CsvHelper と 入力すると [CsvHelper] が出てくるので、選択してインストールします

■ CSVダウンロードボタンを設置する
今回はデフォルトで用意されている Home 画面にボタンを設置しましょう。
[View] フォルダ ⇒ [Home] ⇒ [index.cshtml] を開く

以下のように View ファイルに CSV ダウンロードボタンを a タグで追加しましょう

@{
    ViewData["Title"] = "Home Page";
}

<div class="text-center">
    <h1 class="display-4">Welcome</h1>
    <p>Learn about <a href="https://docs.microsoft.com/aspnet/core">building Web apps with ASP.NET Core</a>.</p>

    @*CSV ダウンロードボタンを追加する*@
    <a asp-action="CsvDownload" class="btn btn-primary">ユーザー CSVダウンロード</a>

</div>

※a タグに asp-action で Controller のアクションを指定することで、自動的に href 属性を補完してくれます。

■ CSV ダウンロード 処理を実装する
ボタンを設置しましたので、最後にCSV ダウンロード処理を実装します。
上記で Action を CsvDownload としましたので、HomeController に CsvDownload アクション を追加して、その中でCSVダウンロード処理を実装していきましょう。

[Controllers] フォルダ ⇒ [HomeController.cs] を開く
以下のように CsvDownload アクションを追加します。

using System;
using System.Collections.Generic;
using System.Diagnostics;
using System.Linq;
using System.Threading.Tasks;
using Microsoft.AspNetCore.Mvc;
using Microsoft.Extensions.Logging;
using CsvDownload.Models;
// Usingを追加する
using System.IO;
using CsvHelper;
using System.Globalization;

namespace CsvDownload.Controllers
{
    public class HomeController : Controller
    {
        private readonly ILogger<HomeController> _logger;
        private readonly Context _context;

        public HomeController(ILogger<HomeController> logger, Context context)
        {
            _logger = logger;

            // コンテキストをコンストラクタで定義する
            _context = context;
        }

        public IActionResult Index()
        {
            return View();
        }

        public IActionResult Privacy()
        {
            return View();
        }

        [ResponseCache(Duration = 0, Location = ResponseCacheLocation.None, NoStore = true)]
        public IActionResult Error()
        {
            return View(new ErrorViewModel { RequestId = Activity.Current?.Id ?? HttpContext.TraceIdentifier });
        }

        /// <summary>
        /// CSVダウンロード
        /// </summary>
        /// <returns>CSVファイル</returns>
        public FileContentResult CsvDownload()
        {
            // CSV ファイル名
            string csvFileName = "ユーザーデータ.csv";

            // メモリを確保する
            using (var memory = new MemoryStream())
            using (var writer = new StreamWriter(memory))
            using (var csv = new CsvWriter(writer, new CultureInfo(0x0411, false)))
            {
                // コンテキストを使用してUsers テーブルのデータを取得する
                List<User> users = _context.Users.ToList();

                // 取得したデータを記録する
                csv.WriteRecords(users);
                writer.Flush(); 
                
                // CSVファイルとして出力する
                return File(memory.ToArray(), "text/csv", csvFileName);
            }
        }
    }
}

■ 動作確認
これで、一通り実装ができましたので、最後に動作確認をしましょう。
ビルドしてホーム画面を開きます。
[ユーザー CSVダウンロード] ボタンが表示されているので、これをクリックするとCSVファイルがダウンロードされます。

ファイルを開くと以下のようにUsers テーブルのデータが登録されていることが確認できます。

これでCSVファイルのダウンロードができるようになりました。
以上が大まかな処理の流れとなります。

備考

■ 一部カラムを取得しないようにしたい
ID のようにCSVダウンロードで必要ないカラムを出力したくない場合があると思います。
そんな時は Model クラスの 出力したくないカラム(プロパティ)に [ignore] 属性(using CsvHelper.Configuration.Attributes; を追加する必要あり)を付与することで対応が可能です。

using CsvHelper.Configuration.Attributes;

namespace CsvDownload.Models
{
    /// <summary>
    /// Users テーブルのモデルクラス
    /// </summary>
    public class User
    {
        [Ignore]
        public int       Id      { get; set; }  // ID プライマリーキー

        public string    Name    { get; set; }  // 名前

        public int       Age     { get; set; }  // 年齢

        public float     Height  { get; set; }  // 身長

        public float     Weight  { get; set; }  // 体重
    }
}

これでファイルをダウンロードするとIDカラムが出力されないようになります。

■ ヘッダー名を変更したい
現状ヘッダーは Model のプロパティ名がそのまま出力されていますが、こちらも変更することが可能です。
方法は、変更したいプロパティに[Name] 属性を付与するだけです。

using CsvHelper.Configuration.Attributes;

namespace CsvDownload.Models
{
    /// <summary>
    /// Users テーブルのモデルクラス
    /// </summary>
    public class User
    {
        [Ignore]
        public int       Id      { get; set; }  // ID プライマリーキー

        [Name("名前")]
        public string    Name    { get; set; }  // 名前

        [Name("年齢")]
        public int       Age     { get; set; }  // 年齢

        [Name("身長")]
        public float     Height  { get; set; }  // 身長

        [Name("体重")]
        public float     Weight  { get; set; }  // 体重
    }
}

これでファイルをダウンロードするとヘッダーが変更されていることが確認できます。

まとめ

いかがでしたでしょうか。
このようにCSVダウンロード機能は、管理システム等ではよく必要とされる機能だと思いますので、少しでも参考になれば幸いでございます。

最後に

私が所属するシステム開発のサービスサイト「SEKARAKU Lab(セカラク ラボ)」を開設しました。
ビヨンドは、サーバーの設計・構築から運用までをワンストップでお任せいただけますので、サーバーサイド開発でお困りの方はお気軽にお問い合わせください。
SEKARAKU Lab:[https://sekarakulab.beyondjapan.com/](https://sekarakulab.beyondjapan.com/)

では、以上となります。
ありがとうございました!

この記事がお役に立てば【 いいね 】のご協力をお願いいたします!
0
読み込み中...
0 票, 平均: 0.00 / 10
5,326
X facebook はてなブックマーク pocket
[2024.6.30 CentOS support ended] CentOS server migration solution

[2024.6.30 CentOS support ended] CentOS server migration solution

[2025.6.30 Amazon Linux 2 support ended] Amazon Linux server migration solution

[2025.6.30 Amazon Linux 2 support ended] Amazon Linux server migration solution

[Osaka/Yokohama] Actively recruiting infrastructure engineers and server side engineers!

[Osaka/Yokohama] Actively recruiting infrastructure engineers and server side engineers!

The person who wrote this article

About the author

Tatsuya Hase

Joined Beyond Co., Ltd. as a new graduate.

We develop web systems (development of services and systems that run on browsers, such as web services, digital content, and business management systems) and game APIs (development of programs that communicate with application games).

We also develop private/custom apps for Shopify.

Originally worked at the Osaka office, but transferred to the Yokohama office in 2019.
His hobbies are baseball/karaoke/anime