Your design must be reliable. This is what I have in my project.
1.) Application.Infrastructure
- Base classes for all business objects, a business collection of objects, data access classes and my user attributes and utilities as extension methods. This defines the overall organization of the behavior of my last .net application.
2.) Application.DataModel
- A typed dataset for a database.
- TableAdapters are expanded to include transactions and other functions that I may need.
3.) Application.DataAccess
- Data Access Classes.
- The actual location where database actions are requested using a basic set of typed data.
4.) Application.DomainObjects
- Business objects and collections of business objects.
- Transfers
5.) Application.BusinessLayer
- Provides manager classes accessible from the presentation layer.
- HttpHandlers.
- My own base page class.
- More stuff here.
6.) Application.WebClient or Application.WindowsClient
- My presentation level
- Accepts links to Application.BusinessLayer and Application.BusinessObjects.
Application.BusinessObjects are used throughout the application, and they move across all layers whenever neeeded [except for Application.DataModel and Application.Infrastructure]
All my queries are determined only by Application.DataModel.
Application.DataAccess returns or accepts business objects as part of any data access operation. Business objects are created using reflection attributes. Each business object is marked with attribute mapping in the target table in the database, and properties in the business object are marked with attribute mapping to the target coloumn in the corresponding database table.
My validation structure allows me to validate each field using a designated ValidationAttribute.
My framrwork makes heavy use of attributes to automate most tedious tasks, such as matching and validation. I can also use the new feature as a new aspect in the framework.
A sample business object will look like this in my application.
User.cs
[TableMapping("Users")] public class User : EntityBase { #region Constructor(s) public AppUser() { BookCollection = new BookCollection(); } #endregion #region Properties #region Default Properties - Direct Field Mapping using DataFieldMappingAttribute private System.Int32 _UserId; private System.String _FirstName; private System.String _LastName; private System.String _UserName; private System.Boolean _IsActive; [DataFieldMapping("UserID")] [DataObjectFieldAttribute(true, true, false)] [NotNullOrEmpty(Message = "UserID From Users Table Is Required.")] public override int Id { get { return _UserId; } set { _UserId = value; } } [DataFieldMapping("UserName")] [Searchable] [NotNullOrEmpty(Message = "Username Is Required.")] public string UserName { get { return _UserName; } set { _UserName = value; } } [DataFieldMapping("FirstName")] [Searchable] public string FirstName { get { return _FirstName; } set { _FirstName = value; } } [DataFieldMapping("LastName")] [Searchable] public string LastName { get { return _LastName; } set { _LastName = value; } } [DataFieldMapping("IsActive")] public bool IsActive { get { return _IsActive; } set { _IsActive = value; } } #region One-To-Many Mappings public BookCollection Books { get; set; } #endregion #region Derived Properties public string FullName { get { return this.FirstName + " " + this.LastName; } } #endregion #endregion public override bool Validate() { bool baseValid = base.Validate(); bool localValid = Books.Validate(); return baseValid && localValid; } }
BookCollection.cs
/// <summary> /// The BookCollection class is designed to work with lists of instances of Book. /// </summary> public class BookCollection : EntityCollectionBase<Book> { /// <summary> /// Initializes a new instance of the BookCollection class. /// </summary> public BookCollection() { } /// <summary> /// Initializes a new instance of the BookCollection class. /// </summary> public BookCollection (IList<Book> initialList) : base(initialList) { } }
this. __curious_geek
source share