Ok.
Let me rephrase something.
When I say "big nasty hack", what I mean is that you don't want "if"
conditions in your UserInfo class based on the CurrentSession being
null/nothing or not.
Why?
Because every time you have a different property, you may have to add that
if statement to it.
Aka, if you have 100 properties, you would have 100 if checks about the
CurrentSession
That's where you code becomes non maintainable.
I think the cleanest solution is this.
Code up your UserInfo object.
Code it up so that it the properties are "dumb" in that you just put in
strings and bools and ints in it.
Make UserInfo serializable.
Create a UserInfoFactory class.
public class UserInfoFactory
private sub new
end sub
public shared function GetUserInfoBase dOnEnvironment as UserInfo
' use the CurrentSession check here
'populate properties of UserInfo based on whether you're in the web
or not
'at least with this approach you have encapsulated in ONE place where
all the if logic is.
'the main point im trying to make is DO NOT code up multiple "if"
statements in the UserInfo class itself.
end function
end class
I understand your concerns. And you're right about the duplication of
effort for the properties.
It looks like you just want to be able to "find the person who is doing the
action" whenever you need that info for a .Save operation.
So here is a little Employee.Save mockup
public class EmployeeControl ler
public sub new
end sub
public sub SaveEmployee ( e as Employee ) 'notice the signature doesn't
have userInfo in it
dim ui as UserInfo
ui = UserInfoFactory .GetUserInfoBas edOnEnvironment ()
dim dataLayerObject as EmployeeData
dataLayerObject = new EmployeeData
dataLayerObject .Save ( e.SSN, e. LastName, e.FirstName ,
u.UserID )
return
end sub
end class
Maybe that looks a little better.
I know you're getting flooded with info, but I would also read
6/5/2006
Custom Objects and Tiered Development II // 2.0
at my blog site (or the may 2006 version for 1.1)
If you still have questions, then maybe go back and reedit your original
post.
............... .
Just to add , the purpose of the
IObjectHolder
was not to be a template for creating other classes like that.
Its purpose was to give you a place to persist an object into memory,
WITHOUT having to write different code for asp.net or winforms.
I think you'd find it useful. Again, it would be for persisting an object
you've already got a hold of.
Lets say you find out that the
GetUserInfoBase dOnEnvironment
takes 10 minutes to run (in a winforms enviroment maybe) (this is all just
speculation to show a point) and generate a UserInfo object because it has
to check ActiveDirectory , and you're AD is slow.
So you decide "Man, I need that info, but its so slow I only want to that
price one time".
So you want to persist that object somewhere.
So in asp.net you say "I'll put it in the Session", And in winforms you say
"I'll throw into into memory as a singleton".
And you start coding away. And boom, you've got Session and winforms code
scattered out everywhere, aka, not easy to maintain.
Here is the method I would use ( talking about my blog)
''---------------------------------------------- abc
dim ui as UserInfo (code from above)
dim ioh as IObjectHolder
ioh = ObjectHolder.Ge tObjectHolder() '' it doesn't care whether or not I'm
in the web or winforms environment, the factory takes care of that for me
ioh.Add ( "SOMEKEY" , ui )
..............
Now its in the cache, and when I need it.
dim ui as UserInfo
ui = ObjectHolder.Ge tObjectHolder() .Item("SOMEKEY" )
if (not (ui is nothing) ) then
'I got the ui from the cache !!
end if
''---------------------------------def
You see the code between -------abc and -------------def
You put that in your biz layer AND ITS THE SAME CODE WHETHER YOURE IN
Asp.net Or winforms.
that's the beauty of the Factory. you're code on teh outside world becomes
cleaner.
because you're only got 1 "currentses sion is nothing" check ( or 2 if you
count the other factory method)
That's what I mean by hacky code. When you can avoid writing the same "if"
statment all over the place, and have it in one place, and simplify your
code because you don't have intermixed asp.net and winforms code every AND
get reuse by pushing it into the biz layer, you're gaining significant
maintenance abilities.
I'll close with this.
The cost of software development is NOT the development time.
Its the maintenance costs.
So its fine to say "hmmm that doesn't look right". But at the same time
give it a serious try.
The argument "I'd have to add an extra class or extra interface" is not a
good one most times.
The design patterns give you the template for how to approach a common
problem. And sometimes you code up some extra files.
But the maintenance will be easier down the road.
Good luck. I think' you've hit some new concepts today!
"Monty" <mo***@communit y.nospamwrote in message
news:ua******** ********@TK2MSF TNGP04.phx.gbl. ..
Hi Sloan,
I am familiar with interface-based programming but, as you guessed, not up
on design patterns. I will research it more (though Rocky's VB 2005 BO
book
is next in the queue), but in defiance of the sound principal "It's better
be quiet and be thought a fool than to open your mouth and prove it", my
initial impression on the difference between our two implementations (your
elegant one and my "whole lot of big nasty hack") is that after about the
3rd or 4th time that I had change something in ~both~
WebSessionObjec tHolder
and InMemoryObjectH older the honeymoon would be over. I am attracted to
the
fact that my "hack" encapsulates all it's functionality into single,
easily
maintainable class (as opposed to spread out between three classes and an
interface), does not duplicate the exact same properties and methods in
two
different places, does not require a helper class and does not add four
files to my solution to maintain. In your implementation, since there will
never be more than two concrete classes that do 99% the same thing except
store themselves a little differently, is it worth all the overhead?
OK, I'm reading your posts again and wonder if you misunderstood my
implementation. You said:
=============== ========
DO NOT DO THIS........... .
Public Class UserInfo
public readonly property IPAddress as string
get
If Nothing = System.Web.Http Context.Current Then
return "IPAddress not available in winforms"
Else 'Web Environment
Return Server(REMOTE_I P_ADDRESS)
End If
end get
end property
That's a whole lot of big nasty hack.
=============== ========
And in the next email you said:
=============== ========
Your factory will return a UserInfo
and you'll still just pass back 1 or the 2 objects, based on that
Nothing check on the CurrentSession object.
Notice you don't have a bunch of "If" statements in the code
saying what the IP address is. Each concrete class takes
care of its own business.
=============== ========
By my prototype doesn't do that at all. The only branching (between WebUI
vs
WinForms) is in the GetInstance method, there is no branching in the
properties. Any relevant user info is stashed in the UserInfo object when
the user logs in (whether it be via web or windows), so there is no need
for
the UserInfo class to reach out to the Server object to get the IP address
if it's in one environment or do something else if it's in another.
Regarding "Each concrete class takes care of its own business", the
"business" is 100% the same, with the only exception of how GetInstance
does
it's magic depending on the environment.
Anyway, I will read up on patterns and perhaps I will see the error of my
ways. Thanks again for the sample app and blog post, it was very helpful.