剛開始應用.NET開發數據庫訪問代碼,實體層的手工編碼是一個相對麻煩而又重復的工作。增加數據庫字段,需要添加實體層類型屬性,其次還要修改數據庫讀寫代碼。在項目初試階段,這種變動太頻繁了,於是根據一些項目的特性,設計了如下的代碼生成器,以減少沒有技術含量的基礎代碼生成工作。
下面以(localhost)上面的Northwind為例子,來看看如何應用它。
在服務器停靠窗體中,添加新的數據庫,選擇Employees表,生成它的Model類型的代碼,也就是實體層。
using System; namespace BusinessEntity { /// <summary> /// 實體類EmployeesEntity /// </summary> public class EmployeesEntity { public EmployeesEntity() { } private int _employeeid; private string _lastname; private string _firstname; private string _title; private string _titleofcourtesy; private DateTime _birthdate; private DateTime _hiredate; private string _address; private string _city; private string _region; private string _postalcode; private string _country; private string _homephone; private string _extension; private byte[] _photo; private string _notes; private int _reportsto; private string _photopath; public int EmployeeID ...... }
部分代碼如下圖所示的,對每個字段添加下划線,再首字母大寫生成對應的屬性。網上常稱這是個貧血的類型定義,沒有適當的方法行為。
再選擇DAL數據訪問代碼,選擇基於Param類型的,或是基於SQL方式的代碼,生成的代碼例子如下
using System; using System.Data; using System.Text; using System.Collections.Generic; using Microsoft.Practices.EnterpriseLibrary.Data; using Microsoft.Practices.EnterpriseLibrary.Data.Sql; using System.Data.Common; namespace Service { /// <summary> /// 數據訪問類EmployeesDAL。 /// </summary> public class EmployeesDAL { public EmployeesDAL() {} /// <summary> /// 是否存在該記錄 /// </summary> public bool Exists(int EmployeeID,string LastName) { StringBuilder strSql=new StringBuilder(); strSql.Append("SELECT COUNT(1) FROM Employees"); strSql.Append(" WHERE EmployeeID="+EmployeeID+" and LastName="+LastName+" "); Database db = DatabaseFactory.CreateDatabase(); DbCommand dbCommand = db.GetSqlStringCommand(strSql.ToString()); int cmdresult; object obj = db.ExecuteScalar(dbCommand); if ((Object.Equals(obj, null)) || (Object.Equals(obj, System.DBNull.Value))) { cmdresult = 0; } else { cmdresult = int.Parse(obj.ToString()); } if (cmdresult == 0) { return false; } else { return true; } } ------ }
最后,生成業務接口,以封裝上面的數據訪問代碼。
using System; using System.Data; using System.Collections.Generic; using BusinessEntity; namespace Service { /// <summary> /// 業務邏輯類EmployeesService /// </summary> public class EmployeesService { private readonly EmployeesDAL dal=new EmployeesDAL(); public EmployeesService() {} #region 成員方法 /// <summary> /// 是否存在該記錄 /// </summary> public bool Exists(int EmployeeID,string LastName) { return dal.Exists(EmployeeID,LastName); } ...... }
在2009年,我寫過一篇文章,指出代碼生成器配合一種小項目結構,以快速應用開發。請參考文章《一種小項目開發結構》,來了解這種結構。我截取一個圖,簡單的概括一下它的基本結構
設計三個層,實體層 BusinessEntity,數據訪問層DataProvider,服務接口層Service,最后是界面層Web應用程序。
ASP.NET Factory代碼生成器能勝任上面的工作,為你減輕大量敲寫重復代碼的工作量。
在2010年的時候,接觸到ORM,並且應用到項目中去。ORM項目有自己的代碼生成器,再加上自己對模板生成有了新的理解和認識,這個代碼生成器就停止維護,一直未進行過修訂,所以如果所下載的源碼中有Bug,請自行調試解決。
這種代碼生成器有一定的優勢,弊端也有,我列舉幾條,供您作出增強方面的參考
1 如果需要改動生成的代碼格式,需要修改代碼,重新編譯,這會帶來新的bug。
2 當時只考慮了SQL Server,沒有對Access,Oracle,MySQL等流行的數據庫進行編碼,也沒有留下擴展的接口。
3 命名規則固定到代碼中,沒有應用配置選項。被生成的實體名,數據訪問DAL方法名,命名空間,都寫死到代碼中,如果需要修改,請自行查找出處。
4 沒有批量代碼生成的功能。如果需要對同一個數據庫的所有表生成所有的實體訪問代碼,則無法做到。
5 沒有同時生成VB和C#兩種代碼。合理的情況下,應該提供同時生成VB和C#兩種格式的代碼,像CodeDom那樣。微軟自己的窗體設計器,就是應用CodeDom,可生成VB或C#的兩種格式的代碼,而只需要一寫編寫,維護一套代碼。
所有源代碼下載地址 http://epn.codeplex.com