|
I am editing this post to remove the sample code as I no longer think it would be a good design.
After more research, it appears that the Data Access Object Design Pattern is a good solution to separate a Data Access API from the business objects.
Example: http://www.tutorialspoint.com/design_pattern/data_access_object_pattern.htm
Comments are welcome.
Thanks!
Carlos.
Original Question: What is the best Design Pattern to separate data access from the business layer?
modified 14-Feb-14 12:03pm.
|
|
|
|
|
Why is it necessary to separate the data layer from the business layer? Are you thinking of changing the data repository? Is there another reason?
|
|
|
|
|
Just to counter the other inference in the other response there are good reasons for having a data layer.
It helps to start with a data model. A data model represents data in the application and although it will often be one to one with database tables/objects that isn't always the case.
Once you have that then your data base layer is created to expose that data model.
This is common enough that there are already generic frameworks for it. NHibernate is one and there are others.
In my experience it is a bad idea to use inheritance as you have suggested. Data models seldom represent inheritance and implementing it like that even when it seems like such models are there is often a problem. This of course is compounded by a poor design where inheritance is used rather than a better choice of attributes and/or composition.
You data layer should not expose anything about the database itself. Often it will be better to have helper classes that do the real work and your exposed classes use those to do the real work.
|
|
|
|
|
Carlos Merighe wrote: ANY COMMENTS OR SUGGESTIONS? STOP SHOUTING!
Carlos Merighe wrote: PLEASE BE SPECIFIC. STOP POSTING TEXT IN ALL-CAPS!
You weren't specific with wich type of comment you expected, so my apologies, I'm grumpy, ignore it if you're not in a good mood.
What's the difference between Oracle and SQL? Does Oracle not use SQL? Did you mean "SQL Server" or "MySQL"?
Second, you don't want two different implementations to load data from a DataProvider that shares an interface; one can handle both scenario's using a db-agnostic interface (the IDbCommands) - there may be variations in the queries, but the infrastructure would be the same. Any ORM worth it's money would provide the same functionality. ORM's are sweet, they keep code nicely readable.
Alternatively, if you want to dive into some examples created from your dataset - take a look at some code-generators like MyGeneration[^]; there's usually multiple templates to create 3-tier applications (and more) - some templates generating complete websites. A benefit is that the code is generated from data that you're (often) familiar with, making it easier to recognize some of the parts (compared to those abstract examples in the books).
Bastard Programmer from Hell
If you can't read my code, try converting it here[^]
|
|
|
|
|
I agree with the comment regarding a shared interface.
But inserting large number of records into Oracle works very differently from SQL/Informix. SQL's bulk loader does not share a common interface with Oracle. It is not important to discuss their interfaces here. Besides, that is a design test at this point.
Guys, but the business layer is not inheriting from the data implementation, such as the Oracle-specific implementation class. The business object Bonus does not know where the data is coming from. Removing the inheritance would mean that a client would be able to access the Name property for the business object, which makes no sense to me. Example:
Bonus obj = new Bonus( new LevelBonus_SQL() );
obj.Name = "some name";
obj.Load(); //It will load from SQL, but the business Bonus object does not know
PROBLEM: Remove the inheritance and I can no longer access obj.Name.
modified 13-Feb-14 17:28pm.
|
|
|
|
|
Carlos A Merighe wrote: PROBLEM: Remove the inheritance and I can no longer access obj.Name.
I use the following model when I create my own layers. Following is pseudo code.
class CustomerPrimitive
{
String name
String address
String telephone.
}
class CustomerDb
{
create(CustomerPrimitive)
update(CustomerPrimitive)
delete(Id id)
List<CustomerPrimitive> query(CustomerPrimitiveQuery)
}
Keep in mind that the 'Primitive' is a Data Model Object and not necessarily a direct table representation. The 'Primitive' must NOT have any significant functionality and must NOT have and database specific code in it.
The database specific code goes in the 'Db' classes. You can add abstractions on top of the above but I haven't found them useful (and I have done it.)
The 'Primitive' types should be in their own space (package, namespace, whatever) which is entirely separate from the 'Db' types.
|
|
|
|
|
Ditch the term "Load"; how about "LoadByName" or "LoadById"? Throw an InvalidOperation if a property is set in a non-loaded (but created) object. Personally, I'd have that argument in the constructor, removing the possibility to create an empty class.
Bastard Programmer from Hell
If you can't read my code, try converting it here[^]
|
|
|
|
|
Have a look at my article[^]
Carlos Merighe wrote: it appears that the Data Access Object Design Pattern is a good solution to separate a Data Access API from the business objects.
I would even say it is mandatory. It makes you think in smaller problems, which in turn makes you build simple and easy solutions to those problems. If you pile up everything into one problem/solution you'll end up with a huge mess.
Also it enforces re-usability, which leads to robust and stable code.
Carlos Merighe wrote: What is the best Design Pattern to separate data access from the business layer?
The one that fits you best. I'm not saying that so I can give you an easy answer. There is no "best" solution. Try out different solutions and see what best fits your needs and coding styles. Depending on the technology you can go old school as in my article or go the new way with LINQ or other technologies. Note that if you're in a company you probably want to use their way of working.
hope this helps.
|
|
|
|
|
You could also use the Unit of Work / Repository pattern for your purposes.
Thanks
JD
http://www.seitmc.com/seitmcWP
|
|
|
|
|
i need design pattern which will do continuous monitoring and evaluating and then further evaluating after certain time period. Working on Windows platform. Need help how or which design pattern to use or what approach to use .
Thanks,
|
|
|
|
|
|
i want which particular is more suitable to scenario which i described.
-- modified 11-Feb-14 3:22am.
|
|
|
|
|
What do you mean which language? Design patterns are concepts, they are language neutral.
Veni, vidi, abiit domum
|
|
|
|
|
bymistake i typed it - "which language" .. i have edited it.. please see it.. I know design patterns concept.. looking for specific pattern suitable for my requirement.
|
|
|
|
|
You first need to do the requirements analysis and design of your application. You can then look at all design patterns and implement where they are most appropriate.
Veni, vidi, abiit domum
|
|
|
|
|
There is no specific design pattern for what you're trying to do. But here are some general pointers:
1. Observer pattern allows you to monitor an object by subscribing to an event and then taking an action when that event occurs.
2. Visitor pattern allows you to perform operations on an element's structure.
3. The Command pattern can be used to encapsulate the command you wish to perform on the monitored objects.
4. To do a periodic or continuous or repetitive task, you usually implement a Timer.
|
|
|
|
|
|
Hi All,
I need to design a system where-in there is lot of decision making and also system needs to be adaptable as and when required.
Looking into above criteria adapter n visitor design pattern come to my mind but not sure. Please suggest design pattern as per above requirement.
I need to develop system in C++ and on Windows platform.
Thanks,
|
|
|
|
|
You should gather the requirements of the system and work out the overall design of it first. Then as you take each part and refine its design, you will see where patterns become appropriate for the actual implementation.
Veni, vidi, abiit domum
|
|
|
|
|
manisha.k.chaubey wrote: I need to design a system where-in there is lot of decision making and also system needs to be adaptable as and when required.
Sounds like a human brain. Good luck with that design.
Other than that actually restricting the domain would be the place to start. Additionally focus on what the users want.
|
|
|
|
|
There is no "do-it-all" design pattern. Each pattern is suited for a specific programming task.
What you need to do here is to build a complex Rules Engine that takes in a set of rules (criteria) and emits a set of ordered steps/actions that need to be performed for the specified rules.
|
|
|
|
|
Here's a question I ask myself for a while every time I start a new web project.
I explain
Architecturally all software on which I worked are more or less designed the same way. roughly:
• A database (transactional)
• A data layer (generated from database)
• A business layer (Web Services)
• A GUI layer (Web application)
• And business rules (without rules)
My question is about the business rules. By business rules I mean all rules that design the software given by your business, workflow or technical limitation. (I'm not talking of rules you put in your business only).
In the application on which I worked I found implemented:
• in the transactional database in the form of constraint or trigger,
• in the layer data often generated from the database,
• in the business layer when it comes to more complex business rules,
• In the GUI layer to alert the user as soon as possible and before triggering a request unnecessarily.
I understand the usefulness of business rules in each of these layers of a program. But the technologies that I have used forced us to rewrite or generate business rules in each of these layers because the languages are different:
• In database trigger and constraint are in SQL
• In data layer business rules are in C#
• In business layer business rules are in C#
• In GUI layer business rules are in JavaScript
My question: Is there a language that can accommodate all business rules in a single place or language? Something that prevents me to rewrite several times in different languages my business rules? I know I cannot check all business rules in one place but some yes. for instance the minimum and maximum character of a password can be check in all layer. Right now I write this rule in 3 different languages in 3 different places (Gui/Javascript, Layers/C# and database constraint).
Sub-question: In case of Web Application what if I use JavaScript with nodejs and Mango database?
B413
|
|
|
|
|
B413 wrote: Is there a language that can accommodate all business rules in a single place or language? No. Even if there were a language that does all[^], there'll still be a difference between validation on the clients' side, and validation on the database-layer.
B413 wrote: My question is about the business rules. By business rules I mean all rules that design the software given by your business, workflow or technical limitation. (I'm not talking of rules you put in your business only).
Your question seems to apply to the database-validation, and all derived checks. BR should be constrained to it's layer.
B413 wrote: Right now I write this rule in 3 different languages in 3 different places (Gui/Javascript, Layers/C# and database constraint). The stringlength-constraint is an easy one; the datalayer in C# could be generated based on the database-schema, and the GUI could use the StringLengthAttribute[^] information to do it's check - that'd mean that there'd be three languages performing the same check in three different places, but with the declaration only in a single place (in this example, the database). There's an abundance of variations on the above.
B413 wrote: • A database (transactional)
• A data layer (generated from database)
• A business layer (Web Services)
• A GUI layer (Web application)
• And business rules(without rules)
That doesn't mean that they're all built that way. A few years ago we considered the database the DAL. It abstracted away a file-system, made data-validation easy, and gave us a uniform way of accessing the data we store. I've also seen quite some code where the BL is a DLL containing classes derived from POCO-classes based on the DB-schema.
If you want a "single language", you'd be looking at the languages that the most restricted environments (in your collection of environments to support) have in common. Database-servers only speak SQL, and browsers usually only JavaScript - but that doesn't mean that they all need a separate implementation. There are some code-generation-tools out there that can do the boring stuff.
Bastard Programmer from Hell
If you can't read my code, try converting it here[^]
|
|
|
|
|
Eddy Vluggen wrote: that'd mean that there'd be three languages performing the same check in three different places, but with the declaration only in a single place (in this example, the database).
The declaration only in a single place because you assume that the code is generated from the database. You generate entities with attributes. But what if
1. You are not working with a SQL server
2. You have business rules you cannot implement in your database
3. You are not working with ASP.NET MVC or WPF
My point of view is that all business rules must be with my model, my entities. partial classes, inheritance, separate check classes, I don't know. What happens in my database is not my problem. As C# developer I don't want to know if my DBA has created constraint or not. I call my check from my GUI. I don't want to write them or generate (writing or generating is the same) them twice. I can do that when I write my GUI with C# classic form. I cannot do that with HTML or ASP.NET MVC.
|
|
|
|
|
I agree with you except that
1. Generating tools to generate from database to business is bad. You give to much power to your database and you repeat the mistakes. I know many developers do that so I expect to argue on this point.
2. As developer a database is just a way to persist my data. It's not my job to create constraint or triggers. (for performance reason I'll perhaps create indexes but that all)
3. It seems increasingly clear that all my BR are a part of the business layer or the entities. If my GUI use the same language than my business layer I can reuse my BR and entities for validation in my GUI.
I still don't understand developers that use HTML/JavaScript as GUI with C# as business layer (web service) because cannot reuse their C# code in their HTML/JavaScript GUI. They don't respect the Don't Repeat Yourself rule.
|
|
|
|