【C#】使用模版方法統一操作行為
在專案開發時,我們通常會對資料庫進行操作,
在平時若我們需要一組特定的資料(Data Model),就會建立一個Function來進行撈取資料,是十分合理的。
但隨著專案越來越大,若要專案中的每位成員都使用相同的流程操作,甚至是統一錯誤的Exception時,可就是一項大工程了!
這個時候我們就可以使用模版方法(Template),不但可以統一操作資料庫的邏輯,更可以增加日後維護的方便性,
只需修改一個地方,即可套用到所有的成員。
首先我們建立一個DBHelper的Class,注意此處都是使用DB的基礎抽象成員(DbConnection,DbCommand...etc),
我們只需要依照自己所需使用的DB類型來傳入正確的類別即可 (如OracleConnection)
在這次例子中,僅僅實作了兩組模版方法ExecuteReaderTemplate及ExecuteNonReaderTemplate,
分別為使用DataReader讀取資料,以及不使用DataReader的模板
using System;
using System.Diagnostics;
using System.Data.Common;
public static class DBHelper
{
public static TResult ExcuteReaderTemplate<TResult>
(Func<DbConnection> connectionSetting, Func<DbCommand> commandSetting, Func<DbDataReader, TResult> dataMapping)
{
DbConnection connection = connectionSetting();
try
{
connection.Open();
}
catch (Exception error)
{
Debug.WriteLine(string.Format("Connection Open Error : {0}", error.Message));
Debug.WriteLine(error.StackTrace);
return default(TResult);
}
DbCommand command = commandSetting();
command.Connection = connection;
DbDataReader reader;
try
{
reader = command.ExecuteReader();
}
catch (Exception error)
{
Debug.WriteLine(string.Format("Execute Reader Error : {0}", error.Message));
Debug.WriteLine(error.StackTrace);
return default(TResult);
}
try
{
TResult data;
data = dataMapping(reader);
return data;
}
catch (Exception error)
{
Debug.WriteLine(string.Format("Data Mapping Error : {0}", error.Message));
Debug.WriteLine(error.StackTrace);
return default(TResult);
}
finally
{
connection.Close();
}
}
public static void ExcuteNonReaderTemplate
(Func<DbConnection> connectionSetting, Func<DbCommand> commandSetting)
{
DbConnection connection = connectionSetting();
try
{
connection.Open();
}
catch (Exception error)
{
Debug.WriteLine(string.Format("Connection Open Error : {0}", error.Message));
Debug.WriteLine(error.StackTrace);
}
DbCommand command = commandSetting();
command.Connection = connection;
try
{
command.ExecuteNonQuery();
}
catch (Exception error)
{
Debug.WriteLine(string.Format("Execute Command Error : {0}", error.Message));
Debug.WriteLine(error.StackTrace);
}
finally
{
connection.Close();
}
}
}
建立好模板方法方法之後,我們可以輕易的將其套用在資料庫連接類別之中,範例如下
(此處使用Oracle做為範例)
using System;
using System.Collections.Generic;
using System.Text;
using System.Data.OracleClient;
public class Data
{
public int ID { get; set; }
public string Name { get; set; }
}
public class DbAccessObj
{
public static Data GetUserById(int id)
{
return DBHelper.ExcuteReaderTemplate<Data>(
connectionSetting,
() =>
{
string commandString = "SELECT * FROM MyTable WHERE ID = " + id;
return new OracleCommand(commandString);
},
(reader) =>
{
reader.Read();
Data tmpData = new Data();
tmpData.ID = reader.GetInt16(0);
tmpData.Name = reader.GetString(1);
return tmpData;
}
);
}
private static OracleConnection connectionSetting()
{
string connectionString = "Data Source=MyServer;User ID=MyName;Password=MyPassword;Unicode=True";
return new OracleConnection(connectionString);
}
}
是不是輕鬆又愉快呢?
模板方法還可以應用在許多地方,可以方便且快速的統一操作行為,未來有機會再跟大家分享囉