Well here's a simplified explanation what I do in my business objects. I
implement an interface, IValidator:
MessageList ValidationMessages {get;}
bool Validate(string,object)
bool ValidateAll(object)
All the above are implemented as public in the business object. I have a
business object for each DB table, but the business object that a form or
page might talk to would likely orchestrate several "table-level" business
objects and present one high-level interface to the presentation layer.
A MessageList is just a simple subclass of
System.Collections.Specialized.StringCollection with a ToString()
implementation that returns all the messages with newlines between them for
easy display. Each Validate() or ValidateAll() call clears the collection
and then adds one or more message to it if the requested validation fails.
Validate() will add zero or one messages, ValidateAll() will add zero or
more messages.
Validate(string,object) takes an attribute name and a value (which can be
either the attribute's native type, or a string representation thereof --
say, a TextBox Value) and determines whether it's valid or not. If it
returns false, it will also stuff a descriptive message in
ValidationMessages.
ValidateAll(object) does all the validations plus any entity-level integrity
checking and produces potentially multiple failure messages.
I use a passive container class to pass records around between tiers; in
"record-level" business objects, ValidateAll() gets one of those containers
to validate. ValidateAll() is normally called automatically just before
persisting the data to the back end, but the presentation layer can call it
directly to verify that all is well before even trying to persist it.
So ... a WinForms app might for example have a TextBox holding a last name
for a person. You might them make a call something like this from the
validation event:
if (this.personBO.Validate(this.Name,this.Text) == false) {
// display messagebox based on this.personBO.ValidationMessages[0]
// and take whatever other actions you wish to
}
In an ASP.NET scenario the logic for saving the page would call the
Persist() method of the business object associated with that page, which
would in turn call ValidateAll() for all tables involved. This would be a
safety net under the JavaScript code that would hopefully enforce the
business rules at the field level, but if that client side code failed, you
could display messages about all the offending fields to the user and have
them fix those fields. And then you could go plug the leak in your
JavaScript.
--Bob
"Jack Addington" <ja********@shaw.ca> wrote in message
news:ux**************@TK2MSFTNGP09.phx.gbl...
I wasn't under the impression that it would be as simple as changing a
'skin' or something but for something as simple as an update that spawns a
database error I would like a common plan to pass the information back to
the presentation.
Going back to my original question, more for the winforms since that has
to work long before I tackle the webform, would you suggest a way to
essentially push a message from a non-visual business layer to the
presentation layer?
"Bob Grommes" <bo*@bobgrommes.com> wrote in message
news:Oq**************@TK2MSFTNGP11.phx.gbl... Jack,
An ASP.NET application is a very different beast. Things like
messageboxes
have to be raised by client-side JavaScript code. Also, that JavaScript
field validation has to replicate to a great extent the business logic
that
resides in your business objects and/or stored procedures -- at least,
it does if you want to provide the kind of feedback users expect from a
rich client.
You can certainly swap in a different presentation layer but the code
reuse
between WinForms and ASP.NET presentation layers just inherently sucks.
If
you stick to Microsoft's postback-heavy model and try to keep as much
logic
on the server as possible, it gets somewhat better, but it'll never just
be
a matter of swapping a few things around no matter how hard you try.
Microsoft has actually backed off from a design goal like this for their
development frameworks. If they can't pull it off, you probably can't
either.
--Bob
"Jack Addington" <ja********@shaw.ca> wrote in message
news:%2****************@tk2msftngp13.phx.gbl... I've got a fairly simple application implementation that over time is
going to get a lot bigger. I'm really trying to implement it in a way that
will
facilitate the growth. I am first writing a WinForms interface and
then need to port that to a web app. I am kinda stuck on a design issue and
need some suggestions / direction.
Basically I have a business layer that I want to use to process any
dataentry logic (row focus changes, data validation etc). I'm hoping
that
I can in time just substitute a web gui for the win gui and not have much
code re-write. Anyhow my problem is how to pass message to the user back to
the GUI layer from the logic layer.
ex) GUI data object lets user change a number and it falls outside the
range.
I have subscribed to the data object's 'dataChanged' event from my
logic layer and have determined that it falls outside the acceptable range.
I basically want to display a popup message that tells the user so. Now
it seems 'wrong' to me to have a reference to system.windows.forms so I
can do a MessageDlg.Show("Bad Value ...") as obviously that won't work with
the web frontend. I don't want to raise an exception because I don't have a
'try ' clause around some sort of 'start edit' on the GUI side.
I've had thoughts that maybe I need a generic function on my frontend
that
handles messages from the logic side??? Is that where an interface
would work? How do I go about making it generic so that I can re-use it for
webforms etc.
thanks so much
jack