SHOEISHA iD

※旧SEメンバーシップ会員の方は、同じ登録情報(メールアドレス&パスワード)でログインいただけます

CodeZine編集部では、現場で活躍するデベロッパーをスターにするためのカンファレンス「Developers Summit」や、エンジニアの生きざまをブーストするためのイベント「Developers Boost」など、さまざまなカンファレンスを企画・運営しています。

5分でわかるActiveReports帳票

5分で"もっと"わかるActiveReports帳票(2008年度版)-帳票アプリケーション設計のポイント(2)

第5回 データモデル設計のポイント

  • X ポスト
  • このエントリーをはてなブックマークに追加

データモデルを設計しよう

 前回は、ActiveReportsを利用した帳票アプリケーションで設計すべきポイントとして、「データモデルの定義」と「帳票レイアウトの定義」の2つがあると説明し、後者の「帳票レイアウトの定義」を中心に解説しました。今回は残っている「データモデルの定義」について解説していきますが、その前に、前回の内容を簡単におさらいしておきましょう。

 帳票レイアウトの定義は「出力構造の定義」と「出力項目の定義」の2工程に分かれます。出力構造の定義では、ユーザーとの打ち合わせから得られたレイアウト案を元に出力構造を洗い出します。この工程では、帳票のレイアウトから繰り返し構造を抽出し、ActiveReportsのレポートファイルに用意された各種ヘッダ/フッタセクションとDetailセクションに対応づけていきます。

 出力構造の定義が終わったら、次は出力項目の定義です。セクション定義済みのレポートファイルにLabelコントロールやTextBoxコントロールを配置して、出力項目の書式やフォント、折り返し設定などを定めていきます。出力項目を表すコントロールのDataFieldプロパティにレポートデータソースの各フィールド名を設定することで、ActiveReportsの帳票アプリケーションは完成します。

データモデルを意識しなくても帳票は作れる?

 帳票アプリケーション開発の現場で使われている設計書を見てみると、出力項目の配置や書式など「帳票レイアウトの定義」は割と丁寧に記述されていることが多いのですが、帳票アプリケーションが読み取るためのデータについてはあまり細かく説明されていないことがあります。直接目にする帳票レイアウトと比べて、データモデルのほうは意識されることが少ない、ということでしょうか。

 ActiveReportsでは、レポートデザイナのDetailセクションに表示されたアイコンをクリックして「レポートデータソース」ダイアログを起動し、データベースの接続やXMLファイルの情報を与えるだけで、(データの形をあまり考えなくても)簡単にデータバインドを実装できます。

 これは間違いなくActiveReportsの大きな長所なのですが、反面、いきあたりばったりの実装でもそこそこ動くアプリケーションができてしまい、複雑なSQLを駆使した帳票の集計ミスが後になって見つかることも少なくありません。

ActiveReportsの「レポート データソース」ダイアログ
ActiveReportsの「レポート データソース」ダイアログ

 帳票アプリケーションを設計するときは、目に見える帳票レイアウトの定義だけでなく、どのような構造のデータを読み取るのかについてもしっかり定義しておくことが重要です。今回は、ActiveReportsのレポートファイルで使うためのデータ構造を設計するポイントについて解説していきたいと思います。

データモデル設計のメリット

 前回、ActiveReportsのレポートファイルで使うためのデータ構造を「データモデル」と呼ぶことにしました。帳票アプリケーションを開発するときは、データモデルを明確に定義しておくことで場当たり的な実装をけん制し、品質の高いアプリケーションを開発できるようになります。

 ActiveReportsでは、レポートデータソースとしてSQL ServerなどのRDBMSや、CSVやXMLといったデータファイルなどさまざまな形式のデータに接続して帳票を出力できます。しかし、どのようなデータソースであってもDetailセクションに定義された1件分のデータを繰り返し出力していくのが基本です。そのため、ActiveReportsを利用した帳票アプリケーションの設計では、RDBのテーブルと同じような「行×列の表形式で表されるデータ構造」をベースにデータモデルを考えていくのがよいでしょう。

 読者の皆さんの中には「このようなものを定義してなんの意味があるのか」と思われる方もいるかもしれません。しかし、帳票アプリケーション設計の段階でデータソースに依存しない形でデータモデルを定義しておくと、データの論理構造と表現形式の分離がはっきりとし、メンテナンス性が向上するというメリットがあります。例えば、それまでXMLファイルを読み込んで出力していた帳票アプリケーションがあったとしましょう。このXMLファイルは帳票アプリケーションのデータモデルに準拠した構造になっています。ここで、同じようにデータモデルに準拠した構造でRDBのテーブルを作れば、XMLベースのファイル帳票アプリケーションがそのまま、データベース帳票アプリケーションとして再利用できるのです。

 この他にも、独立したデータモデルを作っておくと「開発用データベースが準備できるまではテスト用のスタブで仕事を進めておく」といった手段をとることもでき、開発効率の面でもメリットがあります。

表形式のデータモデルを基本に考える
表形式のデータモデルを基本に考える
データソースを帳票レイアウトに直接関連付けると、データソース変更時に修正が必要
データソースを帳票レイアウトに直接関連付けると、データソース変更時に修正が必要
データモデルを考えておくと、レポートデータソースの乗り換えもスムーズ
データモデルを考えておくと、レポートデータソースの乗り換えもスムーズ

 また、レポートデータソースとして指定するSELECT文やXMLファイルを直接読むよりも、データソースとは独立したデータモデルを用意しておくほうが、その帳票が何を出力するのかがわかりやすくなります。データモデルはあくまで抽象的な型の定義なので、ソースファイルとして実装するには具象クラスを使うよりもインタ-フェイスを使うのがよいでしょう。たとえばDetailセクション1件分を表す型をIDetailというインタ-フェイスで定義しておき、データモデル全体はIEnumerable<IDetail>のような形にしておけば、データソースの種類に依存しないモデルを作ることができます。また、IEnumerableインタ-フェイスにしておくことで、LINQによる操作も容易になります。

以下は、先ほど紹介した表形式のデータモデルをC#/VBのインターフェイスとして定義したものです。

データモデルの例(C# 3.0)
public interface IDetail
{
    public int Year { get; set; }
    public int Quarter { get; set; }
    public int Month { get; set; }
    public decimal SalesAmount { get; set; }
}
データモデルの例(Visual Basic 9.0)
Public Interface IDetail
    Property Year() As Integer
    Property Quarter() As Integer
    Property Month() As Integer
    Property SalesAmount() As Decimal
End Interface

 データモデルを用意しておくと、以下のように帳票生成部分のロジックをデータソースと分離することができます。帳票生成部分であるForm_Loadメソッドの中身を変えることなくGenerateDataメソッドを変更するだけで柔軟にデータソースを取り替えることが可能です。

インターフェイスを利用した帳票生成の例(C# 3.0)
private IEnumerable<IDatail> GenerateData()
{
    //データ生成処理を記述
}
private void Form1_Load(object sender, EventArgs e)
{
    IEnumerable<IDetail> data = GenerateData();
    NewActiveReport1 rpt = new NewActiveReport1();
    rpt.DataSource = data.ToList();
    rpt.Run();
}
インターフェイスを利用した帳票生成の例(Visual Basic 9.0)
Private Function GenerateData() As IEnumerable(Of IDetail)
    'データ生成処理を記述
End Function

Private Sub Form1_Load(ByVal sender As System.Object, _
        ByVal e As System.EventArgs) Handles MyBase.Load
    Dim data = GenerateData()
    Dim rpt As New NewActiveReport1
    rpt.DataSource = data.ToList()
    rpt.Run()
End Sub

次のページ
データモデル設計の3ポイント

この記事は参考になりましたか?

  • X ポスト
  • このエントリーをはてなブックマークに追加
5分でわかるActiveReports帳票連載記事一覧

もっと読む

この記事の著者

宮本奈紗(ミヤモトナサ)

株式会社システムインテグレータ ERPソリューション部所属。ERPシステムの設計・開発に従事。業務でActiveReportsを使用。

※プロフィールは、執筆時点、または直近の記事の寄稿時点での内容です

渡辺俊史(ワタナベトシフミ)

株式会社システムインテグレータ パッケージ開発部所属。ECサイト構築パッケージの設計・開発に従事。VSUG(Visual Studio User Group) データベース・データアクセスフォーラムリーダー。blog...

※プロフィールは、執筆時点、または直近の記事の寄稿時点での内容です

この記事は参考になりましたか?

この記事をシェア

  • X ポスト
  • このエントリーをはてなブックマークに追加
CodeZine(コードジン)
https://codezine.jp/article/detail/2949 2015/06/04 13:00

おすすめ

アクセスランキング

アクセスランキング

イベント

CodeZine編集部では、現場で活躍するデベロッパーをスターにするためのカンファレンス「Developers Summit」や、エンジニアの生きざまをブーストするためのイベント「Developers Boost」など、さまざまなカンファレンスを企画・運営しています。

新規会員登録無料のご案内

  • ・全ての過去記事が閲覧できます
  • ・会員限定メルマガを受信できます

メールバックナンバー

アクセスランキング

アクセスランキング