-
N-Tier: help on real world implementation
I have to separate in different machines/servers the different dlls in my n-layered project, I wish to know what would be the most appropriate method to accomplish this. The DAL would be in a different machine and perhaps the BLL would be in a different machine also, I am looking with Web Services as an option here though it would be my first time to delve with web services so I need some guidance here or perhaps you could offer me some alternative route to take other than a web service? I am using DTO (Data Transfer Object) to pass data between layers and I am contemplating, there should be a web service in the DAL that would accept DTOs and pass it to the DAL right? In my current implementation I am using the sample code below to accept, process and pass DTOs (any negative feedback on the implementation is welcome):
Code:
namespace DataAccess
{
public class DataPortal<T> : IDisposable
{
private Methods _dataAccess;
private bool disposed;
public DataPortal()
{
_dataAccess = new SqlServerDatabase();
}
public T FetchOne(string sqlStatement)
{
Type objectType = typeof(T);
object businessObject = null;
// Prepare our query
_dataAccess.PrepareQuery(sqlStatement);
if (_dataAccess.RecordExists())
{
businessObject = Activator.CreateInstance(objectType);
DataRow dr = _dataAccess.GetDataRow();
for (int b = 0; b < dr.Table.Columns.Count; b++)
{
// Map the columns to the object's properties
string columnName = dr.Table.Columns[b].ColumnName;
PropertyInfo field = objectType.GetProperty(columnName);
object value = dr[b];
if (!(value is System.DBNull))
field.SetValue(businessObject, dr[b], null);
else
field.SetValue(businessObject, null, null);
}
}
return (T)businessObject;
}
public bool Insert(Entities.BusinessObject businessObject)
{
//Get the INSERT sql statement
string stringSql = businessObject.SqlStatement;
// Prepare our query
_dataAccess.PrepareQuery(stringSql, CommandType.StoredProcedure);
// Fill the parameter values
for (int a = 0; a <= businessObject.Fields.Count - 1; a++)
{
if (businessObject.Fields[a].IncludeInSql.Equals(true))
{
if (businessObject.Fields[a].FieldValue != null)
InsertClassParameter(businessObject.Fields[a]);
else
_dataAccess.AddParameter(businessObject.Fields[a].FieldName, businessObject.Fields[a].FieldValue);
}
}
int result = (int)_dataAccess.ExecuteActionQuery();
return (result > 0);
}
}
}
I have the ff. concerns which I hope you guys would address:
1. I wish to know if the above code can be converted to equivalent web methods? Or should I use different web methods for each CRUD of the different DTOs?
2. Upon reading I have learned that web services serializes objects on the background so I wish to know if there is a need for me to actually serialize my DTOs before passing them to the web service? Or did I understand it correctly?
3. What are the best practices when utilizing web services in n-tier applications?
TIA
-
Re: N-Tier: help on real world implementation
Your calling application/class need to have a knowledge of the entities you're dealing with. Mark them serializable. Have a look at any sample web service application and you'll see that it's just a matter of creating a method, marking it as a webmethod and writing your code as usual. But you may want to keep it simple as you cannot pass 'state' across the tiers in such a case. Remember, the web is stateless so a call to a web service method must not make use of datareaders (for example) which still persist a connection.
I'm not going to comment on your code right now, but I did notice that you're using System.Reflection in there and I wonder what compelling reason you could possibly have for this.
-
Re: N-Tier: help on real world implementation
Oh and each web method is separate, so there isn't going to be a constructor in which you can initialize a new sqlserverdatabase() object. You have to do this for each call.
Quote:
3. What are the best practices when utilizing web services in n-tier applications?
Every application is different so there isn't a definite answer to this. A few guidelines do exist though, such as "keep things simple!". Think of a web service as a web page that is returning some text to you. You pass it a few parameters, it gives you some text. You use that.
-
Re: N-Tier: help on real world implementation
Quote:
Originally Posted by mendhak
I'm not going to comment on your code right now, but I did notice that you're using System.Reflection in there and I wonder what compelling reason you could possibly have for this.
I wanted a single method to process 'all' my business objects hence the reflection, is there a negative impact by employing such?
-
Re: N-Tier: help on real world implementation
The primary reason for using Reflection, ever, is to find out information about a class you have. It isn't meant to be used in a production environment due to the speed and memory impact that loading the object has. So your method is fine as long as you have... 1 user.
-
Re: N-Tier: help on real world implementation
What? Huh, never thought it had such a consequence. Can I have your suggestions then for an alternative to my method? I have seen some samples that are similar to mine and monkey sees monkey dos... :afrog:
-
Re: N-Tier: help on real world implementation
A single method to process all your business objects is what you said. I need a little more info though. Can I see what you monkeyed, I need a better understanding of how you're using it.
-
Re: N-Tier: help on real world implementation
The code that I posted is what I am referring to, I am just passing all my Business Objects/DTOs to it and it processes it no matter what kind of (e.g. Employee Entity, Salary Entity, etc... ) Business Object it is, though they have a base class name BusinessObject as you can see from the code, then I am just instantiating the object using reflection. Is there any alternative to this implementation? I just don't want to 'always' modify my DAL to include some CRUD operations for certain tables I may add in the database hence I want to have a single CRUD that would process all the business entities for the tables in the database.
I am contemplating, perhaps I could use a keyed collection where it will contain the names of the columns and its corresponding values, will that work? I haven't tried it but it is an idea I am considering though I am not inclined to delve into it if it will also have performance issues.
Thanks!
-
Re: N-Tier: help on real world implementation
So from what I can gather, you are giving up flexibility and performance for the sake of maintenance and scalability.
Design is never easy, you always have to come up with balances. Let's look at your situation - where would this be useful? From a 1000ft view, this is useful if you are constantly and frequently adding new types of business objects to your application. And then, this design makes sense, because I am willing to give up on the performance bit to make it easier to maintain and use by my clients.
Now let's look at the other scenario. If my logic isn't going to change as frequently but only once in a while (regular maintenance scenario), then I'm going to keep things as straightforward as possible. It'll make debugging easier, and I can add new bits in later, easily. The performance will be better.
So what this boils down to is, if you've got a really good reason for doing what you're doing, then do it. One of the biggest design mistakes I've ever seen is often trying to automate everything as much as possible to the point that debugging it becomes a nightmare. It's a great idea in the beginning, but you later realize that the application should never change.
-
Re: N-Tier: help on real world implementation
Reflection isn't the slowest thing in the world. Most of the speed drain that people refer to with reflection is because they combine it with latebinding which is the actual drain. If you reflect known base types or interfaces then the impact is very minimal. Reflection is even more useful when you are using it to search for attributes since you don't need to create an instance of the object to read its attributes, they are on the type.
-
Re: N-Tier: help on real world implementation
Thanks guys. As you can see I want to implement a method similar to the Generics in .Net, I am not sure how Generics works in the background but it seem is great and more efficient like for example suing List instead of arraylist right? That is my goal, to have a Data Access Layer that can receive and process all my business entities. In my method my entities have a base class and that base class is the one declared as the parameter for my CRUDS. If I can find a way to at least make it as efficient as possible then I welcome your suggestions.
Code:
public bool Insert(Entities.BusinessObject businessObject)
And is this not the sense of having an n-tier application, to minimize the changes to be made in the application? That is if I need to add another table then I won't have to changes all the layers, perhaps only the BLL and the GUI or the BLL only?
-
Re: N-Tier: help on real world implementation
It isn't. It may be a mangled and mutated view of BLLs in this day and age, but the original purpose and intent of a BLL is to ensure that the data is valid and processed. It has nothing to do with minimization of changes. Maintenance is what often gets mixed into the process as part of politics/needs, but it isn't the purpose of a BLL.
Anyways, looking back at your code, is it correct to assume that any calls to that method essentially have your code looping through the properties of the class to create parameters for a stored procedure that is yet to be called? Does this mean it's a straightforward set of calls that will always be received and passed as-is to the stored procedure without any logic changes?
-
Re: N-Tier: help on real world implementation
hi man,
Around November 2007 i wrote such an article in Vb.net , but it will be easy to understand. see what i Wrote myber it might help you.
http://www.codeproject.com/KB/vb/N-T...cation_VB.aspx
Hope this Helps
Thanks
-
Re: N-Tier: help on real world implementation
Quote:
Originally Posted by mendhak
Anyways, looking back at your code, is it correct to assume that any calls to that method essentially have your code looping through the properties of the class to create parameters for a stored procedure that is yet to be called? Does this mean it's a straightforward set of calls that will always be received and passed as-is to the stored procedure without any logic changes?
Yes, the processing is the same for all my business entities so the data access layer remains the same even if I add new business entities. My CRUDs for my stored procedures are the same also. Why ask?
-
Re: N-Tier: help on real world implementation
Just inquiring further. It further means that it's actually your database which is your BLL (by definition), since any special circumstances you want to make will have to be made in there without disturbing the reflection. Or you end up subclassing one of your entities in order to override certain methods to perform any validation that you may some day need.
Now instead of getting more pointers, how about answering some questions? :D What changes do you anticipate in the future? What are you looking for with this design?
-
Re: N-Tier: help on real world implementation
Quote:
Originally Posted by mendhak
Just inquiring further. It further means that it's actually your database which is your BLL (by definition), since any special circumstances you want to make will have to be made in there without disturbing the reflection. Or you end up subclassing one of your entities in order to override certain methods to perform any validation that you may some day need.
Now instead of getting more pointers, how about answering some questions? :D What changes do you anticipate in the future? What are you looking for with this design?
I am not sure yet what changes will come, its just that since you frowned on my method then I am looking for ways to optimize it as much as possible though without changing the pattern I already since it is working fine as I need it...
All the validations are done in the BLL so its okay to make some changes in there, what I want to remain intact is the DAL though as I've said I want some improvements on it if it is even possible. :-)
-
Re: N-Tier: help on real world implementation
Since using a web service is stateless then how do we handle transactions when using one?
-
Re: N-Tier: help on real world implementation
"Use the tool for the job and not the other way around." Web services are stateless as you said, and there is no support for transactions. Either you don't use web services or you call the web methods such that each call is a single transaction in itself from the [WebMethod] onwards.
If you're lucky, the WS-C/T specification will become a standard soon and vendors will start implementing it into their transaction protocols, but until then you are to treat web services as they are currently meant to be treated - loosely coupled. A need for transaction represents a need for tight coupling and therefore would require a different solution.
-
Re: N-Tier: help on real world implementation
-
Re: N-Tier: help on real world implementation
Quote:
Originally Posted by mendhak
"Use the tool for the job and not the other way around." Web services are stateless as you said, and there is no support for transactions. Either you don't use web services or you call the web methods such that each call is a single transaction in itself from the [WebMethod] onwards.
If you're lucky, the WS-C/T specification will become a standard soon and vendors will start implementing it into their transaction protocols, but until then you are to treat web services as they are currently meant to be treated - loosely coupled. A need for transaction represents a need for tight coupling and therefore would require a different solution.
Can I not use even TransactionScope? Since the WebServices will return something which will indicate success or failure then perhaps there is someway I could Rollback if something failed...
-
Re: N-Tier: help on real world implementation
Are these transactions short lived or of a longer durations?
How many rows in how many tables might be affected by this open transaction??
-
Re: N-Tier: help on real world implementation
Quote:
Originally Posted by szlamany
Are these transactions short lived or of a longer durations?
How many rows in how many tables might be affected by this open transaction??
For now its just two tables with a parent-child relationship where the maximum record for the child for each parent is 20. Any suggestions Sir?
-
Re: N-Tier: help on real world implementation
So you are looking to lock one parent with the 20 children while some web-page has that selection up for modification - right?
And there is a good likely hood that some other user will attempt to get this same set of records?
Would they be changing the parent?
One of the child records?
Adding a new child record??
Since this is a "real world" thread - give me some real info on what's being maintained here.
-
Re: N-Tier: help on real world implementation
The scenario is something like this...
StartTransaction
SaveParent
If SaveParent = True
SaveChildren
If SaveChildren = False Then
RollBack
Else
CommitTransaction
End If
Else
RollBackTransaction
End if
I've handled the locking mechanism already, I am just looking for the most appropriate solution to the above problem, it was very easy to accomplish in VB6.0 but Transactions in .Net is quite 'difficult' for me as of now... :)
-
Re: N-Tier: help on real world implementation
Can you not pass the parent+child together and handle the transaction within your stored procedure?
-
Re: N-Tier: help on real world implementation
Can't you test in the SPROC that the data has not changed before making the update and report back the fact the "data is not in it's original state" to the user?
-
Re: N-Tier: help on real world implementation
I am now okay with the transactions...
I have another query which I hope you guys could address also:
I am using a Web Service as a top layer in accessing my database, what I wish to know is will the web methods need to start a thread for each call to the methods of the Data Access Layer?
-
Re: N-Tier: help on real world implementation
Mendhak & szlamany are spot on with a couple of points above, namely to look at serialising objects, and this one:
Quote:
Can you not pass the parent+child together and handle the transaction within your stored procedure?
I would like to suggest rather than web services, which utlises XML & SOAP and is limited to simply the HTTP communication protocal, to look at remoting as an alternative.
As above, it's still definitely worth reading up on the ISerializable interface, however using remoting will allow for a far greater depth of alteration and scalability should you wish to alter this in the future (for example, you can pass the serialized object between servers using the much faster protocal of simple TCP/IP instead and should you wish to change this to use HTTP in the future, you should just need to alter a config file or 2 [depending upon how you write it]).
Webservices are easier to get to grips with and write a solution with, but I'd say the harder to learn & write remoting framework would best fit your question here...
-
Re: N-Tier: help on real world implementation
Quote:
Originally Posted by mendhak
A single method to process all your business objects is what you said. I need a little more info though. Can I see what you monkeyed, I need a better understanding of how you're using it.
Ugh, I am monkey #2 here? Time to go Monkey #3! :D May I hear what you will say on Monkey #3? (If only I can be the Wolf)
-
Re: N-Tier: help on real world implementation
Hmmmnn, this should also be worth considering when I need to optimize my current method.