667481 members! Sign up to stay informed.

Sponsored Links


Resources

Enterprise Java
Research Library

Get Java white papers, product information, case studies and webcasts

News News News Messages: 94 Messages: 94 Messages: 94 Printer friendly Printer friendly Printer friendly Post reply Post reply Post reply XML XML XML

Using Annotations to add Validity Constraints to JavaBeans?

Posted by: Floyd Marinescu on March 18, 2005 DIGG
When building domain models in Java, contraints to fields in a class are typically defined and enforced in the code, usually in setter methods. While us OO developers love to see this type of data validation logic expressed in code, Anders Holmgren argues that it can lead to duplication of validation code across tiers, or even worse, developers purposefully not validating in certain places where they should be, in order to avoid such duplication.

One solution would be to declaratively define constraints that could then be re-used throughout your application, similar to how Web Services standards use XML Schema to define constraints on data that is exchanged.

In a new article on java.sun.com, Anders Holmgren proposes the use of annotations to add validity constraints to objects, declaratively, like this:
public class Address {
    @MaxLength(20)
    public String street;

    ....
}
Anders also suggests standardizing them so that we could realize a number of benefits such as:

  • Allowing introspection of constraints
  • When used with a good validation framework it would result in little, if any, application code would be required for enforcement.
  • Constraints could theoretically be defined in your classes once, and then automatically applied (re-used in other tiers).
  • It would allow the implementation of sophisticated validation frameworks that could even be integrated into existing validation frameworks.
  • Existing IDE support for annotations would make contraint annotations easy to work with.
Anders implemented some annotations and also provided an example validation framework. While Anders acknowledges some limitations to the approach, he believes it to be a pragmatic and useful solution to an important problem.

What do you think?

Threaded replies

·  Using Annotations to add Validity Constraints to JavaBeans? by Floyd Marinescu on Fri Mar 18 17:04:49 EST 2005
  ·  Using Annotations to add Validity Constraints to JavaBeans? by Leonard Gurevich on Fri Mar 18 17:42:21 EST 2005
    ·  Using Annotations to add Validity Constraints to JavaBeans? by Mileta Cekovic on Fri Mar 18 18:49:10 EST 2005
      ·  Using Annotations to add Validity Constraints to JavaBeans? by Leonard Gurevich on Sat Mar 19 10:23:46 EST 2005
        ·  Constraints in the database by Johannes Brodwall on Sat Mar 19 11:32:12 EST 2005
          ·  Constraints in the database by Radu-Adrian Popescu on Sat Mar 19 12:02:22 EST 2005
            ·  Constraints in the database by Chris Jennings on Sat Mar 19 12:46:37 EST 2005
              ·  Constraints in the database by Radu-Adrian Popescu on Sun Mar 20 15:36:21 EST 2005
                ·  Constraints in the database by Mark Nuttall on Sun Mar 20 16:48:40 EST 2005
                  ·  Constraints in the database by Radu-Adrian Popescu on Mon Mar 21 00:01:33 EST 2005
                    ·  Constraints in the database by Mark Nuttall on Mon Mar 21 08:51:44 EST 2005
                  ·  Constraints in the database by Radu-Adrian Popescu on Mon Mar 21 00:16:50 EST 2005
                    ·  Constraints in the database by Mark Nuttall on Mon Mar 21 08:55:34 EST 2005
                      ·  Constraints in the database by Radu-Adrian Popescu on Mon Mar 21 09:24:53 EST 2005
                        ·  Constraints in the database by Mark Nuttall on Mon Mar 21 09:53:02 EST 2005
                          ·  Constraints in the database by Paolo Guccione on Mon Mar 21 10:13:37 EST 2005
                            ·  Constraints in the database by Mark Nuttall on Mon Mar 21 10:38:25 EST 2005
                              ·  Constraints in the database by Paolo Guccione on Mon Mar 21 11:41:14 EST 2005
                                ·  Constraints in the database by Radu-Adrian Popescu on Mon Mar 21 11:56:47 EST 2005
                                ·  Constraints in the database by Mark Nuttall on Mon Mar 21 12:14:49 EST 2005
                                  ·  Constraints in the database by Mark Nuttall on Mon Mar 21 12:16:52 EST 2005
                                  ·  Constraints in the database by Jacob Hookom on Mon Mar 21 12:26:33 EST 2005
                                    ·  Constraints in the database by Juozas Baliuka on Mon Mar 21 12:59:45 EST 2005
                                    ·  Constraints in the database by Paolo Guccione on Mon Mar 21 13:23:57 EST 2005
                                      ·  Constraints in the database by Jacob Hookom on Mon Mar 21 17:52:13 EST 2005
                                        ·  Constraints in the database by Mark Nuttall on Mon Mar 21 23:27:02 EST 2005
                                          ·  Constraints in the database by Jacob Hookom on Tue Mar 22 00:15:28 EST 2005
                                          ·  Constraints in the database by Radu-Adrian Popescu on Tue Mar 22 03:19:05 EST 2005
                                            ·  Constraints in the database by Jacob Hookom on Tue Mar 22 03:23:35 EST 2005
                                              ·  Constraints in the database by Radu-Adrian Popescu on Tue Mar 22 03:54:35 EST 2005
                                              ·  Constraints in the database by Paolo Guccione on Tue Mar 22 04:20:16 EST 2005
                                                ·  Constraints in the database by Mark Nuttall on Tue Mar 22 08:54:28 EST 2005
                                                  ·  Files, files by Radu-Adrian Popescu on Tue Mar 22 08:57:45 EST 2005
                                                    ·  Files, files by Mark Nuttall on Tue Mar 22 09:03:22 EST 2005
                                                    ·  files, files - finally it is said by Matthew Pope on Sat Apr 23 08:40:34 EDT 2005
                                                ·  Constraints in the database by Jacob Hookom on Tue Mar 22 11:00:25 EST 2005
                                        ·  Constraints in the database by Sony Mathew on Tue Mar 22 23:13:00 EST 2005
                                          ·  Constraints in the database by Radu-Adrian Popescu on Wed Mar 23 02:22:48 EST 2005
                                          ·  Constraints in the database by Jacob Hookom on Wed Mar 23 11:25:35 EST 2005
                          ·  Constraints in the database by Radu-Adrian Popescu on Mon Mar 21 10:31:25 EST 2005
                            ·  Constraints in the database by Mark Nuttall on Mon Mar 21 10:57:58 EST 2005
                              ·  Constraints in the database by Radu-Adrian Popescu on Mon Mar 21 11:02:53 EST 2005
                    ·  Constraints in the database by Mark Nuttall on Mon Mar 21 09:08:12 EST 2005
                      ·  Constraints in the database by Jacob Hookom on Wed Mar 23 11:58:19 EST 2005
                        ·  Constraints in the database by Paolo Guccione on Wed Mar 23 12:35:41 EST 2005
                          ·  Constraints in the database by Mark Nuttall on Wed Mar 23 12:50:12 EST 2005
                            ·  Constraints in the database by Jacob Hookom on Wed Mar 23 13:34:15 EST 2005
                          ·  Constraints in the database by Jacob Hookom on Wed Mar 23 13:15:41 EST 2005
                            ·  Constraints in the database by Paolo Guccione on Thu Mar 24 04:16:00 EST 2005
                              ·  Constraints in the database by Radu-Adrian Popescu on Thu Mar 24 18:16:19 EST 2005
                            ·  Constraints in the database by Radu-Adrian Popescu on Thu Mar 24 18:10:05 EST 2005
                ·  Constraints in the database by Chris Jennings on Mon Mar 21 00:47:39 EST 2005
                  ·  Constraints in the database by Radu-Adrian Popescu on Mon Mar 21 01:59:20 EST 2005
          ·  Constraints in the database by Leonard Gurevich on Sat Mar 19 12:43:28 EST 2005
          ·  Constraints in the database by Chester Chen on Sat Mar 19 14:48:03 EST 2005
    ·  We have to distinguish between the use cases of validation by Adrian Neagomir on Sat Mar 19 07:30:21 EST 2005
      ·  We have to distinguish between the use cases of validation by Brian Miller on Mon Mar 21 14:29:12 EST 2005
    ·  Using Annotations to add Validity Constraints to JavaBeans? by Brian Miller on Mon Mar 21 14:22:15 EST 2005
  ·  Using Annotations to add Validity Constraints to JavaBeans? by Alessandro Santini on Fri Mar 18 18:01:35 EST 2005
    ·  Using Annotations to add Validity Constraints to JavaBeans? by Mileta Cekovic on Fri Mar 18 18:51:14 EST 2005
      ·  Using Annotations to add Validity Constraints to JavaBeans? by surajeet dev on Sat Mar 19 05:20:57 EST 2005
  ·  Good idea with Commons-Validator by Archimedes Trajano on Fri Mar 18 19:32:24 EST 2005
  ·  Validations should stay only where needed by Bin Sun on Fri Mar 18 20:36:03 EST 2005
    ·  Validations should stay only where needed by Joseph Ottinger on Fri Mar 18 21:34:46 EST 2005
    ·  Validations should stay only where needed by Alessandro Santini on Sat Mar 19 03:07:22 EST 2005
  ·  Using Annotations to add Validity Constraints to JavaBeans? by Jacob Hookom on Fri Mar 18 21:59:02 EST 2005
  ·  Annotations are 2nd choice by John Doe on Sat Mar 19 10:17:33 EST 2005
    ·  Annotations are 2nd choice by Radu-Adrian Popescu on Sat Mar 19 11:41:51 EST 2005
    ·  Annotations are 2nd choice by Ragnar Westad on Mon Mar 21 04:36:29 EST 2005
      ·  Annotations are 2nd choice by Bill Burke on Mon Mar 21 09:45:15 EST 2005
  ·  Using Annotations to add Validity Constraints to JavaBeans? by Agent Smith on Sat Mar 19 15:07:34 EST 2005
    ·  Using Annotations to add Validity Constraints to JavaBeans? by Agent Smith on Mon Mar 21 01:06:31 EST 2005
  ·  I use this technique for about half year by Eugene Lucash on Sun Mar 20 04:45:06 EST 2005
  ·  Using Annotations to add Validity Constraints to JavaBeans? by han theman on Sun Mar 20 04:50:18 EST 2005
  ·  OK to prevent a value from being persisted, but... by Dries Bellen on Mon Mar 21 04:15:47 EST 2005
    ·  OK to prevent a value from being persisted, but... by Paolo Guccione on Mon Mar 21 05:27:00 EST 2005
      ·  OK to prevent a value from being persisted, but... by Juozas Baliuka on Mon Mar 21 06:52:43 EST 2005
        ·  OK to prevent a value from being persisted, but... by Mark Nuttall on Mon Mar 21 09:04:08 EST 2005
          ·  OK to prevent a value from being persisted, but... by Juozas Baliuka on Mon Mar 21 10:37:07 EST 2005
      ·  OK to prevent a value from being persisted, but... by Dries Bellen on Mon Mar 21 08:37:36 EST 2005
  ·  Using Annotations to add Validity Constraints to JavaBeans? by Duncan Mills on Mon Mar 21 06:45:57 EST 2005
    ·  Using Annotations to add Validity Constraints to JavaBeans? by Jens Voss on Mon Mar 21 08:34:01 EST 2005
  ·  Reinventing the past by Amin Mansuri on Mon Mar 21 10:24:55 EST 2005
    ·  Validations and Annotations by Matthew Inger on Mon Mar 21 10:45:31 EST 2005
      ·  Validations and Annotations by Mark Nuttall on Mon Mar 21 11:01:48 EST 2005
      ·  Validations and Annotations by Bill Burke on Mon Mar 21 11:07:11 EST 2005
        ·  Validations and Annotations by Jacob Hookom on Mon Mar 21 11:40:50 EST 2005
    ·  Reinventing the past by Erik Engbrecht on Mon Mar 21 13:44:08 EST 2005
    ·  Reinventing the past by Sony Mathew on Mon Mar 21 14:58:55 EST 2005
      ·  Reinventing the past by Jacob Hookom on Mon Mar 21 15:41:52 EST 2005
      ·  Reinventing the past by Stephan Albers on Tue Mar 22 05:59:33 EST 2005
        ·  constaint and design by contract by Michel Rondeau on Tue Mar 22 08:50:02 EST 2005
      ·  Reinventing the past by Jason Carreira on Tue Mar 22 10:07:34 EST 2005
        ·  Reinventing the past by Sony Mathew on Tue Mar 22 23:48:43 EST 2005
  ·  declarative constraints == separation of concerns by Bill Schneider on Tue Mar 22 15:31:12 EST 2005
  Message #162385 Post reply Post reply Post reply Go to top Go to top Go to top

Using Annotations to add Validity Constraints to JavaBeans?

Posted by: Leonard Gurevich on March 18, 2005 in response to Message #162381
In *real word* applications validations done using data in database. So IMHO this is very limited.

  Message #162387 Post reply Post reply Post reply Go to top Go to top Go to top

Using Annotations to add Validity Constraints to JavaBeans?

Posted by: Alessandro Santini on March 18, 2005 in response to Message #162381
Yet another stupid idea. Now is the time for annotation hype and everybody will try to use it, properly or not.

It looks like the hype about stupid and senseless scripting. Just invent something, spread the word and hope you will get famous.

BE PRAGMATIC!

  Message #162389 Post reply Post reply Post reply Go to top Go to top Go to top

Using Annotations to add Validity Constraints to JavaBeans?

Posted by: Mileta Cekovic on March 18, 2005 in response to Message #162385
In *real word* applications validations done using data in database. So IMHO this is very limited.

Wow, what a pile of nonsense in a couple of words.

  Message #162390 Post reply Post reply Post reply Go to top Go to top Go to top

Using Annotations to add Validity Constraints to JavaBeans?

Posted by: Mileta Cekovic on March 18, 2005 in response to Message #162387
Yet another stupid idea. Now is the time for annotation hype and everybody will try to use it, properly or not.It looks like the hype about stupid and senseless scripting. Just invent something, spread the word and hope you will get famous.BE PRAGMATIC!

This is not stupid nor unpragmatic! Metadata approach to programming can save you a lot of time in some circumstances, although this is not applicable to every situation.

  Message #162393 Post reply Post reply Post reply Go to top Go to top Go to top

Good idea with Commons-Validator

Posted by: Archimedes Trajano on March 18, 2005 in response to Message #162381
I think this would be a good idea with commons-validator.

  Message #162395 Post reply Post reply Post reply Go to top Go to top Go to top

Validations should stay only where needed

Posted by: Bin Sun on March 18, 2005 in response to Message #162381
IMHO, the constraints shouldn't stay in the Java models. They are business logic, not intrinsic for JavaBeans.

If we need to change the length constraints for strings frequently according to business strategies, must we recode and recompile related JavaBeans? It's better to stay as a runtime configurable property.

  Message #162397 Post reply Post reply Post reply Go to top Go to top Go to top

Validations should stay only where needed

Posted by: Joseph Ottinger on March 18, 2005 in response to Message #162395
Why couldn't you have the annotation apply a validation... that it looked up at runtime?

  Message #162398 Post reply Post reply Post reply Go to top Go to top Go to top

Using Annotations to add Validity Constraints to JavaBeans?

Posted by: Jacob Hookom on March 18, 2005 in response to Message #162381
Actually, I beat Anders Holmgren to the punch back in January with an article at OnJava.com:

http://www.onjava.com/pub/a/onjava/2005/01/19/metadata_validation.html

Funny, he brings up the same points as I did a couple months before.....

  Message #162407 Post reply Post reply Post reply Go to top Go to top Go to top

Validations should stay only where needed

Posted by: Alessandro Santini on March 19, 2005 in response to Message #162395
IMHO, the constraints shouldn't stay in the Java models. They are business logic, not intrinsic for JavaBeans.If we need to change the length constraints for strings frequently according to business strategies, must we recode and recompile related JavaBeans? It's better to stay as a runtime configurable property.

+1

That's exactly what I think. Now the hype is to spread annotations like cheese on a pizza.

  Message #162410 Post reply Post reply Post reply Go to top Go to top Go to top

Using Annotations to add Validity Constraints to JavaBeans?

Posted by: surajeet dev on March 19, 2005 in response to Message #162390
This is not stupid nor unpragmatic! Metadata approach to programming can save you a lot of time in some circumstances, although this is not applicable to every situation.
Annotation of any member of a class or to a Class,itelf,can be achieved through configuration settings. XML is more suitable for any attribute oriented programming.

XML files used during deployment are likely to have support for hot-deployment, by many tools. Though the same is possible for java source code,it may not be supported by non-sophisticated tools.

Regards
Surajeet

  Message #162414 Post reply Post reply Post reply Go to top Go to top Go to top

We have to distinguish between the use cases of validation

Posted by: Adrian Neagomir on March 19, 2005 in response to Message #162385
Yes having constraint validation is very important but in general we should distinguish between “syntactic” validation and business logic validation. Usually the earlier we can apply this validations the better it is. Early validation can be done in most of the cases only for syntactic rules while for the business logic constraints the checking for consistency is possible only in the business tier or inside the database.
One should also consider that detecting a constraint validation at some random point in the execution stack is futile. The places where this checking is done should be precisely specified ensuring that at that particular point proper recovery is possible. Such points are well defined in specialized frameworks (e.g. Struts Validator for input validation).
I strongly support declarative approaches since they reduce code complexity but I don’t think that such generalization as mentioned here is required. For simple cases with little reuse is easier to write code than to plug in your own validator. Again the truth is rarely pure and never simple.

Adrian

  Message #162422 Post reply Post reply Post reply Go to top Go to top Go to top

Annotations are 2nd choice

Posted by: John Doe on March 19, 2005 in response to Message #162381
In my opinion annotations/pragma/macros is, why C++ is ugly and hard to learn. If you want simple validity constraints then they should reside in the language spec. What's bad about a new String(20) or an int(0..10000)?

I know, Sun claims Java to be a "stable" language, but it isn't anyway.

chris

  Message #162423 Post reply Post reply Post reply Go to top Go to top Go to top

Using Annotations to add Validity Constraints to JavaBeans?

Posted by: Leonard Gurevich on March 19, 2005 in response to Message #162389
In *real word* applications validations done using data in database. So IMHO this is very limited.
Wow, what a pile of nonsense in a couple of words.

May I ask why is it "pile of nonsense" (Yea, I misspelled *world*)

  Message #162427 Post reply Post reply Post reply Go to top Go to top Go to top

Constraints in the database

Posted by: Johannes Brodwall on March 19, 2005 in response to Message #162423
In *real word* applications validations done using data in database. So IMHO this is very limited.
Wow, what a pile of nonsense in a couple of words.
May I ask why is it "pile of nonsense" (Yea, I misspelled *world*)

I am not the author of the first reponse, but I dare to guess a few reasons: First, the example in the original article validates before going to the database. This can give better responsivity, better error messages, and better error handling. Plus the domain objects will be validated before you execute other business logic with them! Second, if you want this kind of validation in the database, you start treading into the territory of stored procedures and triggers, I am not sure that's such a nice place to be. Third, most *real world* java applications also validate in the domain objects. If you don't, you probably don't want to use domain objects in the first place, as they would at best be anemic, at worst error prone (if they have logic that must work despite validation errors). Anemic domain models (aka DTOs) is IMHO the worst anti-pattern in the history of Java.

If you don't have domain object, this approach (and possibly J2EE) is not a good match for you. If you have domain objects, you'd want to validate in them, not (only) in the database.

  Message #162428 Post reply Post reply Post reply Go to top Go to top Go to top

Annotations are 2nd choice

Posted by: Radu-Adrian Popescu on March 19, 2005 in response to Message #162422
In my opinion annotations/pragma/macros is, why C++ is ugly and hard to learn.
Pragmas are compiler directives. There' needed. Get over it.
Macros are fine as long as you know what you're doing. There's a crusade against them, that's cool with me because I've seen them used wisely and very efectively.
And while I'm at it, C++ is the most advanced, beautiful and well thought out programming language - at least in the systems programming class. The templates alone are wonderous.
And it's hard to learn if students are lazy, if it's taught like pascal++ or GUI development tool or just badly and because it's a very, and I mean *very* complex beast.

  Message #162433 Post reply Post reply Post reply Go to top Go to top Go to top

Constraints in the database

Posted by: Radu-Adrian Popescu on March 19, 2005 in response to Message #162427
Anemic domain models (aka DTOs) is IMHO the worst anti-pattern in the history of Java.

First off DTOs preceede Java. Secondly why would you call them domain models, even if anemic?

That aside, care to explain why are they such a menace?

  Message #162436 Post reply Post reply Post reply Go to top Go to top Go to top

Constraints in the database

Posted by: Leonard Gurevich on March 19, 2005 in response to Message #162427
In *real word* applications validations done using data in database. So IMHO this is very limited.
Wow, what a pile of nonsense in a couple of words.
May I ask why is it "pile of nonsense" (Yea, I misspelled *world*)
I am not the author of the first reponse, but I dare to guess a few reasons: First, the example in the original article validates before going to the database. This can give better responsivity, better error messages, and better error handling. Plus the domain objects will be validated before you execute other business logic with them! Second, if you want this kind of validation in the database, you start treading into the territory of stored procedures and triggers, I am not sure that's such a nice place to be. Third, most *real world* java applications also validate in the domain objects. If you don't, you probably don't want to use domain objects in the first place, as they would at best be anemic, at worst error prone (if they have logic that must work despite validation errors). Anemic domain models (aka DTOs) is IMHO the worst anti-pattern in the history of Java.If you don't have domain object, this approach (and possibly J2EE) is not a good match for you. If you have domain objects, you'd want to validate in them, not (only) in the database.

OK, most business applications are using database. Domain objects validations are using data from database. I did not mention stor procs. IMHO using annotaion it's similar to validations using javascript: sometimes useful, but limited to simple things.

  Message #162437 Post reply Post reply Post reply Go to top Go to top Go to top

Constraints in the database

Posted by: Chris Jennings on March 19, 2005 in response to Message #162433
Anemic domain models (aka DTOs) is IMHO the worst anti-pattern in the history of Java.
First off DTOs preceede Java. Secondly why would you call them domain models, even if anemic?That aside, care to explain why are they such a menace?

DTO is a transport pattern that keeps behavior out and focusses on the data. IMHO it might as well be called DTS (Data Transport Struct). If all you have representing your domain is DTOs then you're maybe not using OO as well as it could be used. Instead you're probably using the Transaction Script pattern. Martin Folwer has things to say about this, and Domain Driven Design, by Eric Evans is a good read too.

My experience is that folks don't feel Transaction Script is a menace (in that *real world* place that keeps coming up). My experience is also that applications get pretty darn complex and that Transaction Script only goes so far. When I've had a rich domain model it's made life easier. Not only did it keep domain data and behavior better contained and expresive, it also helped me to make better facades, which in turn lead to clearer transport boundaries (where the DTOs came in).

I've also found it very hard to get the idea of rich domain models accepted as a core approach in projects I've been on. I'm not sure why. Maybe I'm to feisty. But it feels more like I'm run over by inertia and that patterns in J2EE and SOA seem to lead folks away from rich domains. Again, I don't know why, but I think it's because those things are mostly about transport because they are about distributed applications.

$0.02
,boz

  Message #162443 Post reply Post reply Post reply Go to top Go to top Go to top

Constraints in the database

Posted by: Chester Chen on March 19, 2005 in response to Message #162427
The paper shows an interesting idea. But annotation based validation is a bit too static. For example, if MaxLength is now changed from 20 to 40. One have to recompile the code (let me know if I am wrong here).

But if you store the maxlength in database, you can simply update the database without any code and/or deployment changes.

Store constraint DATA in database, does not necessarily mean valid data IN database with stored procedures or trigger. One can and should still validate in Java code. If one knows the constraints are static and will not change, one can read the constraint condition into memory and cache it. And the Java code validates against the cached constraints, there is no performance penaltiese. If the constraints are sometime changes, the code should have mechanisms to refresh the cache by periodically pooling or event driven update. Thus the validation is against latest constraint data instead of the stale data.

One approach, which I haven't tried myself, is may be use database to store constraint data but use AOP to validate the constraints. Define the point-cut for the place to be validate and write advice to centralize the validation.

The pros :
1. It centralize the logic of validation. it only has one place to maintain the code.
2. If new validation is needed, one only add new point-cut to the advice.
3. The object does not explicitly call out to validate against the constraints.

The cons :

It seems violating the OO principal: as each object should performs it's own validation.

As I said, I havn't tried myself, just throw some idea out.

  Message #162445 Post reply Post reply Post reply Go to top Go to top Go to top

Using Annotations to add Validity Constraints to JavaBeans?

Posted by: Agent Smith on March 19, 2005 in response to Message #162381
Do you test validation rules with JUnit?

I mean such rules like maxLength(20), minValue(5), minSize(1), notNull(), unique() and so on.

  Message #162468 Post reply Post reply Post reply Go to top Go to top Go to top

I use this technique for about half year

Posted by: Eugene Lucash on March 20, 2005 in response to Message #162381
Not so cleanly, but helpful.

I wander when other obvious ideas will get to
thouse PR-writers. I assume that next article will be
about some technique a year old.

  Message #162469 Post reply Post reply Post reply Go to top Go to top Go to top

Using Annotations to add Validity Constraints to JavaBeans?

Posted by: han theman on March 20, 2005 in response to Message #162381
I have lived with annotations in .NET for several years and find it suprisingly hard to communicate its usage to team members and library users. I think annotations can be very useful, but the world is not ready, it seems.

  Message #162492 Post reply Post reply Post reply Go to top Go to top Go to top

Constraints in the database

Posted by: Radu-Adrian Popescu on March 20, 2005 in response to Message #162437
Chris, I know what DTO is and what it's good for. You said they're the worst anti-pattern ever, for Java at least. I didn't think that's a reasonable thing to say, that's all.
The DTOs live at system borders - borders with the database, remote systems, GUIs and whatnot. What's inside these borders - it can very well be a procedural or domain driven design, I don't think that has any relevance on the use of DTO. What I'm saying is that maybe you wanted to warn against some problems but picked the wrong fight.

  Message #162497 Post reply Post reply Post reply Go to top Go to top Go to top

Constraints in the database

Posted by: Mark Nuttall on March 20, 2005 in response to Message #162492
Chris, I know what DTO is and what it's good for. You said they're the worst anti-pattern ever, for Java at least. I didn't think that's a reasonable thing to say, that's all.The DTOs live at system borders - borders with the database, remote systems, GUIs and whatnot.
Pretty much what he is saying is wrong with them. They are not needed anywhere except maybe remoting - but I've not needed them there either. If you need "separation" between the "layers" use interfaces..

  Message #162513 Post reply Post reply Post reply Go to top Go to top Go to top

Constraints in the database

Posted by: Radu-Adrian Popescu on March 21, 2005 in response to Message #162497
Mark, DTOs are structs. How can they not be needed ? Of course they're needed at system boundaries, it's simply not feasable to getXXX() 10 times to obtain all Address components when that can lead to cache checks, remote invocation and whatnot, when you really just need like 384 bytes of data.

  Message #162514 Post reply Post reply Post reply Go to top Go to top Go to top

Constraints in the database

Posted by: Radu-Adrian Popescu on March 21, 2005 in response to Message #162497
Also Mark cheap advice on interfaces is just so September already! Live up to the hype. Layers have since become services, or service-oriented. I'm not sure why you're quoting separation as "separation" - you don't really mean it, is separation actually "separation" i.e. it's just all in our heads? Also those were not layers (or is it "layers"?) but systems. And you're not sending your database interfaces are you?
And Chris never actually said DTOs are bad per se but lack of a strong (as opposed to anemic or weak) domain model is, although even that might work in the "real world" - quotes again, "hello" is "this the" Matrix ?

  Message #162516 Post reply Post reply Post reply Go to top Go to top Go to top

Constraints in the database

Posted by: Chris Jennings on March 21, 2005 in response to Message #162492
Chris, I know what DTO is and what it's good for. You said they're the worst anti-pattern ever, for Java at least. I didn't think that's a reasonable thing to say, that's all.The DTOs live at system borders - borders with the database, remote systems, GUIs and whatnot. What's inside these borders - it can very well be a procedural or domain driven design, I don't think that has any relevance on the use of DTO. What I'm saying is that maybe you wanted to warn against some problems but picked the wrong fight.

Uh. I dind't say anything was the worst anti-pattern ever. Is this realy a fight? Maybe I did pick the wrong one. Hmmm.

,boz

  Message #162519 Post reply Post reply Post reply Go to top Go to top Go to top

Using Annotations to add Validity Constraints to JavaBeans?

Posted by: Agent Smith on March 21, 2005 in response to Message #162445
Do you test validation rules with JUnit?I mean such rules like maxLength(20), minValue(5), minSize(1), notNull(), unique() and so on.
Can someone please quickly answer on this? Thanks.

  Message #162522 Post reply Post reply Post reply Go to top Go to top Go to top

Constraints in the database

Posted by: Radu-Adrian Popescu on March 21, 2005 in response to Message #162516
Uh. I dind't say anything was the worst anti-pattern ever.
Uh. You actually did:
Anemic domain models (aka DTOs) is IMHO the worst anti-pattern in the history of Java.


  Message #162528 Post reply Post reply Post reply Go to top Go to top Go to top

OK to prevent a value from being persisted, but...

Posted by: Dries Bellen on March 21, 2005 in response to Message #162381
I think it's nice that everyone spills his/her guts on the proper place/method to validate. But I'm missing something crucial from a user perspective: suppose you do use annotations, you'll still need a way to make clear to the user that invalid data was entered. That's where you'll need either a new generic mechanism to capture the error/exception, or again some custom code. So where's the added value in using annotations?

  Message #162530 Post reply Post reply Post reply Go to top Go to top Go to top

Annotations are 2nd choice

Posted by: Ragnar Westad on March 21, 2005 in response to Message #162422
What's bad about a new String(20) or an int(0..10000)?

I completely agree, and I've been missing that in Java since its inception. I became used to that kind of constructs when implementing and using a C++ library for ASN.1 in the early 90's and it seems like the obvious way to specify simple constraints. ASN.1 has such constraints built into the language, like INTEGER(0..99) and NumericString (SIZE (12)).

Can anyone explain why this would not work in Java and possible negative effects?

That said, I like the way the article covers the different aspects of the topic and accepting the current state of affairs in the Java world, annotations seems to be a good second choice.

/Ragnar

  Message #162537 Post reply Post reply Post reply Go to top Go to top Go to top

OK to prevent a value from being persisted, but...

Posted by: Paolo Guccione on March 21, 2005 in response to Message #162528
I think it's nice that everyone spills his/her guts on the proper place/method to validate. But I'm missing something crucial from a user perspective: suppose you do use annotations, you'll still need a way to make clear to the user that invalid data was entered. That's where you'll need either a new generic mechanism to capture the error/exception, or again some custom code.

+1

Catching the error is nothing, providing a user-friendly error message is everything.
So where's the added value in using annotations?

As for DB triggers and procs, I have seen and written validation code that raises custom DB exceptions, with understandable messages, used to maximum effectiveness. In a client-server environment this is probably the best way to validate. Maybe not in J2EE, though, since the SQL exception is unlikely to be rethrown to the presentation layer.

If annotation validation includes a reference to a human-readable, localizable error message, then it is a definite help, since it can be used easily and with maximum effectiveness in the presentation layer.

  Message #162547 Post reply Post reply Post reply Go to top Go to top Go to top

Using Annotations to add Validity Constraints to JavaBeans?

Posted by: Duncan Mills on March 21, 2005 in response to Message #162381
Focusing on the actual suggestion here, I think that the major problem is that it's only addressing validation within the narrow focus of Java Code itself.
What if my O/R mapping is metadata driven rather than based on beans / POJOs?
What if I want to reuse the constraints across the Service and presentation layers?
What if I want to provide site customisation of a constraint throughout the whole stack?

I think that it's better to take a step back and view constrain modeling as a more abstract framework task that can be defined in a standard way and applied as required on a layer per layer basis. Commons Validator in Struts provides an implementation of this kind of approach, although its approaching it from the UI up which is probably not the best way.
If we look for a good hook point for standardised validation then the proposal for abstracted Data Binding proposed in JSR227 would seem to fit the bill as it's a natural choke point in any case, and already has a rich description of the data.

  Message #162551 Post reply Post reply Post reply Go to top Go to top Go to top

OK to prevent a value from being persisted, but...

Posted by: Juozas Baliuka on March 21, 2005 in response to Message #162537
I think all constraints must be in database. UI or "input mask" can not manage data integraty, there are many interfaces to access database. User friendly messages are important, but it is not a good reason to ignore database constraints. I think it is better to duplicate validation or generate it from DB metadata than to break data.

  Message #162566 Post reply Post reply Post reply Go to top Go to top Go to top

Using Annotations to add Validity Constraints to JavaBeans?

Posted by: Jens Voss on March 21, 2005 in response to Message #162547
What if my O/R mapping is metadata driven rather than based on beans / POJOs?

Interesting point. Could this be unified somehow? Could perhaps the Hibernate annotations be somehow re-used in the above way?

Regards,
Jens

  Message #162567 Post reply Post reply Post reply Go to top Go to top Go to top

OK to prevent a value from being persisted, but...

Posted by: Dries Bellen on March 21, 2005 in response to Message #162537
If annotation validation includes a reference to a human-readable, localizable error message, then it is a definite help, since it can be used easily and with maximum effectiveness in the presentation layer.

That is indeed a good use, but in some cases this can cause even more issues. I just think of i18n...

  Message #162570 Post reply Post reply Post reply Go to top Go to top Go to top

Constraints in the database

Posted by: Mark Nuttall on March 21, 2005 in response to Message #162513
Mark, DTOs are structs. How can they not be needed ? Of course they're needed at system boundaries, it's simply not feasable to getXXX() 10 times to obtain all Address components when that can lead to cache checks, remote invocation and whatnot, when you really just need like 384 bytes of data.

I understand that issue.

But what is the difference between, for instance, Person(a domain object) and PersonDTO?

  Message #162571 Post reply Post reply Post reply Go to top Go to top Go to top

Constraints in the database

Posted by: Mark Nuttall on March 21, 2005 in response to Message #162514
Also Mark cheap advice on interfaces is just so September already!
Yes, it was for free.
 Live up to the hype. Layers have since become services, or service-oriented. I'm not sure why you're quoting separation as "separation" - you don't really mean it, is separation actually "separation" i.e. it's just all in our heads?
I'm going to have to guess what you meant. Yes, some of it is in peoples heads. The Entity EJB issue is not.
Also those were not layers (or is it "layers"?) but systems. And you're not sending your database interfaces are you?
I'm not "sending" my database anything. And yes, I am using interfaces.

  Message #162574 Post reply Post reply Post reply Go to top Go to top Go to top

OK to prevent a value from being persisted, but...

Posted by: Mark Nuttall on March 21, 2005 in response to Message #162551
I think all constraints must be in database.
If you make the db your integration point and don't want to duplicate logic then will will have too.
I think it is better to duplicate validation or generate it from DB metadata than to break data.
Not all constraints can be generated from metadata. Only RI and column types/sizes. There are many other things that would have to be enforced in triggers and stored procs. And hopefully no one has screwed up the model (that never happens).

  Message #162576 Post reply Post reply Post reply Go to top Go to top Go to top

Constraints in the database

Posted by: Mark Nuttall on March 21, 2005 in response to Message #162514
http://www.javadude.com/articles/

  Message #162577 Post reply Post reply Post reply Go to top Go to top Go to top

Constraints in the database

Posted by: Radu-Adrian Popescu on March 21, 2005 in response to Message #162571
OK, this is getting tiresome. You may live in an EJB world and have EJB issues - I don't. DTOs are not something that came about with EJB. As most pattern guides will also tell these are just simple data structures, objects by value, used at system boundaries. You cannot expose your Customer's information by presenting an interface as that will lead to several round-trips in order to fetch first, last names etc. You also do not exchange interfaces with other systems that you interact with: for instance, the database.

  Message #162580 Post reply Post reply Post reply Go to top Go to top Go to top

Annotations are 2nd choice

Posted by: Bill Burke on March 21, 2005 in response to Message #162530
What's bad about a new String(20) or an int(0..10000)?
I completely agree, and I've been missing that in Java since its inception. I became used to that kind of constructs when implementing and using a C++ library for ASN.1 in the early 90's and it seems like the obvious way to specify simple constraints. ASN.1 has such constraints built into the language, like INTEGER(0..99) and NumericString (SIZE (12)).Can anyone explain why this would not work in Java and possible negative effects?That said, I like the way the article covers the different aspects of the topic and accepting the current state of affairs in the Java world, annotations seems to be a good second choice./Ragnar

Something like this is quite possible if you combine Annotations and AOP. See my article at OnJava.com for concrete examples.

Some people call annotations "hype", but if you're using XDoclet you're already using them. Sure people will abuse them, but they are a huge opportunity to simplify Java development. We see it as an opportunity to add pluggable syntax/keywords to Java. I think we should be encouraging articles such as this.

Also, on a related note, Dean Wampler (formerly a Rational guy) has a project that combines Design By Contract, annotations, and AOP.

http://www.contract4j.org/

JBoss AOP has a similar project:

http://www.jboss.org/wiki/Wiki.jsp?page=DesignByContractAspect

Bill

  Message #162581 Post reply Post reply Post reply Go to top Go to top Go to top

Constraints in the database

Posted by: Mark Nuttall on March 21, 2005 in response to Message #162577
OK, this is getting tiresome. You may live in an EJB world and have EJB issues - I don't. DTOs are not something that came about with EJB. As most pattern guides will also tell these are just simple data structures, objects by value, used at system boundaries. You cannot expose your Customer's information by presenting an interface as that will lead to several round-trips in order to fetch first, last names etc. You also do not exchange interfaces with other systems that you interact with: for instance, the database.
I don't live in an ejb world. But I do live in a distributed world. And I don't need simple data structures. I don't have round tripping issues. The database is not a system in my world. It is a technology and is used as part of my system.

What you are describing as a problem IS the problem many have with Entity EJBS.

Why do you need structs vs full-fledged domain objects? If a remote method returns a DTO, can it not return a domain object?

I'm not trying to be jerk. Please take a look at the link I provided. I've had to go into too many systems and remove all the unnecessary struct/dto/array code - or at least push it to the boundaries.
Also, check out Martin Fowlers Architecture book on how to deal with dto's/structs when you do have to use them.

  Message #162583 Post reply Post reply Post reply Go to top Go to top Go to top

Constraints in the database

Posted by: Paolo Guccione on March 21, 2005 in response to Message #162581
Why do you need structs vs full-fledged domain objects? If a remote method returns a DTO, can it not return a domain object?

Real-world example: suppose your domain object is persisted through ORM, or some objects have permanent connections to resources. I had this problem last year when we made intensive use of Hibernate Objects with lazy instantiations of attributes and associations. The mapped objects, if transfered to the web layer, could trigger an unwanted DB query if a "lazy" property was accessed. The master architect chose to use DTO to bypass this problem, limiting mapped objects to EJB internal use. Of course we had to write a lot of code that just copied data from Domain Objects to DTO and vice versa.

And yes, I know that the object can be detached from the Hib Session. This is exactly the solution I imagine for this year's work. Still, a not-so-skilled programmer could make some embarassing mistakes if the Domain Objects are too "smart".

  Message #162584 Post reply Post reply Post reply Go to top Go to top Go to top

Reinventing the past

Posted by: Amin Mansuri on March 21, 2005 in response to Message #162381
I predict that if such constructs like

@MaxLength(20)
public String street;

catches on then we'll later want to say

@Constraint(StreetType)
public String street;

Why?

Whenever you start constraining data you invariably run into typing. You'll want some nice way of saying "all names are size 20" or "all currency strings have this format" and so on. So the need arises to name common constraint sets the same thing, or you end up maintaining it in many places.

That is why Pascal allows you to say stuff like:

type
  arrayType = Array[1..20] of Integer;

and C had typedef. Some dbs allow you to specify your own types too (if I recall properly).


But this all makes me wonder why we don't just say:

public Street aStreet;

since the class Street would allow you to maintain such constraints on the data but using a more common OO technique.

  Message #162585 Post reply Post reply Post reply Go to top Go to top Go to top

Constraints in the database

Posted by: Radu-Adrian Popescu on March 21, 2005 in response to Message #162581
It's not necesarily a problem with EJB/entity. It's a problem for distributed systems as well.
Take for instance a login/account_info example, IDL:
module bank {
struct account_info_dto {
long id;
long balance2dec;
string currency;
};
interface account_info {
long getId();
long getBalance2dec();
string getCurrency();
};

interface accounting {
account_info_dto login(in string username, in string password);
account_info login_with_if(in string username, in string password);
};
};

Using login() you need 1 call to validate and get back account information for a client. Using login_with_if() you need 4, one for login_with_if() and 3 more getId(), getBalance2dec(), getCurrency().
login_with_if() does not return a domain object, it returns an object reference. login() returns a struct, a Java bean, a POD. I fail to see how you do not have round-trip issues, this is a basic... issue.

I've take a look at the link provided. And yes, that's where the struct/dto/array code lives - at boundaries, what I've been saying all along. The database is not a technology - it's a data system (amazingly it even has an S at the end to stand proof for it). Not much different than a remote client. With the database you talk in terms of data, never interfaces, business logic or whatnot. Data and services are all that's left at systems boundaries. Data is DTO, services are interfaces.

  Message #162586 Post reply Post reply Post reply Go to top Go to top Go to top

OK to prevent a value from being persisted, but...

Posted by: Juozas Baliuka on March 21, 2005 in response to Message #162574
It is possible to generate "input validation" for "CHECK" constraints too. But this stuff can work for trivial cases only. It is common to have different "views" of data. "DATE" field in database and "year","month","day" fields in input form. I see no way to avoid duplication, if user needs cool error messages.

  Message #162587 Post reply Post reply Post reply Go to top Go to top Go to top

Constraints in the database

Posted by: Mark Nuttall on March 21, 2005 in response to Message #162583
Hmmm. Sounds like DTOs are the least of your worries. :(

Thanks for sharing your experience. A possible way to remove the attribute copying is to use delegation. A good IDE will generate the delegation methods. If the DTO/struct/array is trully just that (no logic at all), it'll work and save you some effort.

Personally, I would have solved it a different way, but since you've got to deal with it, try the above suggestion.

  Message #162589 Post reply Post reply Post reply Go to top Go to top Go to top

Validations and Annotations

Posted by: Matthew Inger on March 21, 2005 in response to Message #162584
In general, i've found several things about validations:

1. Validation at the time of property setting is problematic at best. It requires proper order of setting if you have dependent properties. Say for instance, you have a "startDate" and "endDate", which are properly set to "1/1/2005" and "2/1/2005", respectively. If you try to set the "startDate" to "2/2/2005" it will give you an error because the "end" date is after the start date, even though the very next call might set the start date to a later date.

2. Using annotations for complex validations is extremely hard to achieve. Consider that individual objects may have custom validations which validate dependent fields against one another (ie. the startDate and endDate as above). This would require not only having to write the validation class, but writing an annotation class to go along with it, and having to somehow tie the two together (you could make an annotation on your annotation type which indicated a class which supplied the annotation behavior). In addition, if you change the available properties on the validation, you now have to change the annotation as well. Not exactly an ideal solution.


Personally, I prefer the XML approach with the use of method interceptors. Basically, you create a validator declaratively (we're using spring), and then create a dynamic proxy object around your service. The dynamic
proxy is given a method specification and a validator id
which is to be called on a specific parameter at a given index.

<bean id="MyValidator" class="..">..</bean>
<bean id="_MyService" ...>...</bean>
<bean id="MyService" class="ValidatorProxyFactoryBean">
   <property name="target"><ref bean="_MyService"></property>
   <property name="props">
      <entry key="insert"><value>0,MyValidator</value></entry>
   </property>
</bean>

Since it's easier to build up complex validators in XML than it is in annotations, this seems to be the much more effective approach. Yes, i would prefer using annotations (and in that case, my proxy above would simply find the validator from the object being validated, rather than from a bean in the file), but the lack of inheritance, and the restriction on not having multiple instances of an annotation on single element makes this extremely difficult.

  Message #162591 Post reply Post reply Post reply Go to top Go to top Go to top

Constraints in the database

Posted by: Mark Nuttall on March 21, 2005 in response to Message #162585
The database is not a technology - it's a data system (amazingly it even has an S at the end to stand proof for it). Not much different than a remote client. With the database you talk in terms of data, never interfaces, business logic or whatnot. Data and services are all that's left at systems boundaries. Data is DTO, services are interfaces.

Yes it is a system. But not an external system when an application is modeled. If you've done any UML or the old precedure modeling the database is not shown as a system. In process modeling the store is within the system that uses it.

So when my application retrieves non-transient objects from where they are peristed, a domain object is rehydrated with out the use of dto.

In reference. login() - I do the same thing you do, only I return a domain object.

  Message #162592 Post reply Post reply Post reply Go to top Go to top Go to top

Validations and Annotations

Posted by: Mark Nuttall on March 21, 2005 in response to Message #162589
In general, i've found several things about validations:...
I usually do object level validations. So I ask the object if it is valid or allow it to notify whoever cares that it is valid or invalid. So while a date object might have its own validation (is it a date), the object it is an attribute of might have other requirements of it.

  Message #162594 Post reply Post reply Post reply Go to top Go to top Go to top

Constraints in the database

Posted by: Radu-Adrian Popescu on March 21, 2005 in response to Message #162591
I do the same thing you do, only I return a domain object.
Whatever that means. It either has struct semantics or not.

  Message #162596 Post reply Post reply Post reply Go to top Go to top Go to top

Validations and Annotations

Posted by: Bill Burke on March 21, 2005 in response to Message #162589
but the lack of inheritance, and the restriction on not having multiple instances of an annotation on single element makes this extremely difficult.

Please expand on lack of inheritance. Personally, I don't care if an annotation cannot extend another annotation as IMO, I think it is better to just write another annotation. But, the fact that an annotation cannot be inherited by an overriding method is a problem. (@Inherit works on class annotations though).

You can have multiple annotations on a single element by writing a wrapping array annotation, i.e.:

public @inhterface EJBs {
  EJB[] value();
}

@EJBs({
    @EJB(name="foo"),
    @EJB(name="bar")
})
public class MyBean ...

In the past year working with the JCP and such, I've found they are pretty receptive to feedback. We're now on the J2SE committee so, we'll put in our input on this. Its up to the rest of you to post feedback to the appropriate feedback mail lists.

Bill

  Message #162602 Post reply Post reply Post reply Go to top Go to top Go to top

Validations and Annotations

Posted by: Jacob Hookom on March 21, 2005 in response to Message #162596
but the lack of inheritance, and the restriction on not having multiple instances of an annotation on single element makes this extremely difficult.
Please expand on lack of inheritance.

I wrote an article for OnJava on this very same topic back in January and I do talk about how to provide intrinsic behavior to annotations and provide pseudo inheritance---

http://www.onjava.com/pub/a/onjava/2005/01/19/metadata_validation.html

Cheers!

  Message #162603 Post reply Post reply Post reply Go to top Go to top Go to top

Constraints in the database

Posted by: Paolo Guccione on March 21, 2005 in response to Message #162587
A possible way to remove the attribute copying is to use delegation. A good IDE will generate the delegation methods. If the DTO/struct/array is trully just that (no logic at all), it'll work and save you some effort.

Agreed. Indeed, it is what I would have done to pass data from the DTO to the Struts FormBean, which was another, almost equal object. Incidentally, the FormBean added only validation logic to the DTO. However, we managed to copy data in that case, too (and yes, we managed to copy the data from object to object twice - don't ask me why, it was not my decision).

However, delegation is not a solution for the still-mapped object problem. If the invocation of an accessor method can trigger an undesirable side effect due to the internal "logic" of the domain object, the delegator is as dangerous as the object because it invokes the accessor.
I do the same thing you do, only I return a domain object.

Whatever that means. It either has struct semantics or not.

Hmm, this discussion is becoming interesting, although a bit off-topic. I am currently designing a new system and want to get rid of past errors. Let me summarize the terms, as I understand them:

A Domain Object is an object that does not follow any special requirement but being the Java representation of a Entity that has been modeled at requirement analysis time. It could (and should) contain some business logic, at least data validation. A Domain Object may be persisted via ORM. A Domain object might be not serializable.

A DTO is the serializable copy of a Domain Object (JavaBean or C / CORBA struct). It has no logic inside, and all of its properties are settable by external object via accessors. It is always serializable.

A "Service Implementor" (my terminology) is an object that conforms to some framework's constraints (EJB, Spring, etc.) and as such might not be inserted in a simple hierarchy of Java Objects. The framework manages persistence, remoteness and resource management.

If I understand it, the trouble with Domain Objects is that at layer border they could be passed to a remote client only by reference (EJB or CORBA interface-like). And this means statefulness and subsequent calls of remote accessors (a questionable practice in J2EE).

Did I get the point?

  Message #162607 Post reply Post reply Post reply Go to top Go to top Go to top

Constraints in the database

Posted by: Radu-Adrian Popescu on March 21, 2005 in response to Message #162603
With the exception of "and all of its properties are settable by external object via accessors." yes, you did get the point.
It's a chunk of data. Accessor as seen in the 2nd account_info (the interface, which may very well be a proper domain object) are evil, they call back to the server.

  Message #162608 Post reply Post reply Post reply Go to top Go to top Go to top

Constraints in the database

Posted by: Mark Nuttall on March 21, 2005 in response to Message #162603
A Domain Object is an object that does not follow any special requirement but being the Java representation of a Entity that has been modeled at requirement analysis time.
If this is true then there is no need for this -
A DTO is the serializable copy of a Domain Object (JavaBean or C / CORBA struct).

Just make the Domain object serializable. No need to make a copy.

If you use Hibernate, use ver 3.0 and the new Eclipse tools to generate domain objects from the database structure. See what interface they implement.

  Message #162609 Post reply Post reply Post reply Go to top Go to top Go to top

Constraints in the database

Posted by: Mark Nuttall on March 21, 2005 in response to Message #162608
A Domain Object is an object that does not follow any special requirement but being the Java representation of a Entity that has been modeled at requirement analysis time.
If this is true then there is no need for this -
A DTO is the serializable copy of a Domain Object (JavaBean or C / CORBA struct).
Just make the Domain object serializable. No need to make a copy.If you use Hibernate, use ver 3.0 and the new Eclipse tools to generate domain objects from the database structure. See what interface they implement.

Oh yeah, and check out AOP to help separate out the persistance, communiction and transportation concerns.

  Message #162610 Post reply Post reply Post reply Go to top Go to top Go to top

Constraints in the database

Posted by: Jacob Hookom on March 21, 2005 in response to Message #162608
A Domain Object is an object that does not follow any special requirement but being the Java representation of a Entity that has been modeled at requirement analysis time.
If this is true then there is no need for this -
A DTO is the serializable copy of a Domain Object (JavaBean or C / CORBA struct).
Just make the Domain object serializable. No need to make a copy.If you use Hibernate, use ver 3.0 and the new Eclipse tools to generate domain objects from the database structure. See what interface they implement.

I took an opposite approach with DTO's and Domain objects-- because we support multiple applications within the company I work at, we created DTO's that map 1:1 with our tables. We then have Domain objects that delegate state to DTO's.

I really don't like the term Domain objects since they are moreover driven by Application requirements, not general business requirements. Example: OrderSession has an OrderDTO, but the OrderSession coordinates behavior such as validation and updating based on the requirements of the application flow, not some general domain specifications. Business rules are best outlined in stateless procedures that act upon behaviorless DTO's-- to some this may seem an odd approach, but it greatly increases reusability as your 'Domain' objects now just coordinate DTO state with stateless business procedures according the application requirements.

http://hookom.blogspot.com/2004/12/corporate-developer.html

  Message #162615 Post reply Post reply Post reply Go to top Go to top Go to top

Constraints in the database

Posted by: Juozas Baliuka on March 21, 2005 in response to Message #162610
Business rules are best outlined in stateless procedures that act upon behaviorless DTO's-- to some this may seem an odd approach, but it greatly increases reusability as your 'Domain' objects now just coordinate DTO state with stateless business procedures according the application requirements.
This stuff is known as "course grained model", so it is "object oriented" too and there is nothing odd to express entities as structs and procedures in data driven or distributed application. "Domain object" or "Entity" is just a concept and there are many right ways to implement concept. I prefer "course grained model" if application is not a kind of graphical editor too.

  Message #162622 Post reply Post reply Post reply Go to top Go to top Go to top

Constraints in the database

Posted by: Paolo Guccione on March 21, 2005 in response to Message #162610
I took an opposite approach with DTO's and Domain objects-- because we support multiple applications within the company I work at, we created DTO's that map 1:1 with our tables. We then have Domain objects that delegate state to DTO's.I really don't like the term Domain objects since they are moreover driven by Application requirements, not general business requirements. Example: OrderSession has an OrderDTO, but the OrderSession coordinates behavior such as validation and updating based on the requirements of the application flow, not some general domain specifications.

Hmm, I did something similar myself in 2000 working as a OO designer for IBM. This because we were forbidden to use EJB, which was not that bad considering we had to work with WAS 3.5 (i.e. EJB 1.0 !!! ). When the data was sent to the Presentation Layer, only the DTO passed through, the Domain Object stayed in the business layer.

However, I am now convinced that this design was a partial mistake on my part. Maybe the lack of OSS technology at that time left me no other choice, but in recent times I noticed that the J2EE gurus tend to dislike all this overusage of DTOs. At that time they were called VOs, and I suspect they were renamed because people started to use theme everywhere instead of where they are needed - at layer interface.
Business rules are best outlined in stateless procedures that act upon behaviorless DTO's-- to some this may seem an odd approach, but it greatly increases reusability as your 'Domain' objects now just coordinate DTO state with stateless business procedures according the application requirements.

Again, I have designed like this myself, in the past. But this looks a lot like the anemic model schema, which Fowler considers an antipattern. I am not so convinced that this is the right solution, though you DO need DTOs at some point in an application.

  Message #162626 Post reply Post reply Post reply Go to top Go to top Go to top

Reinventing the past

Posted by: Erik Engbrecht on March 21, 2005 in response to Message #162584
.But this all makes me wonder why we don't just say:public Street aStreet;since the class Street would allow you to maintain such constraints on the data but using a more common OO technique.

Because then we'd be called aStreet.toString() all over the place because the only time we don't want it to act like a string is when it's value is being set.

  Message #162636 Post reply Post reply Post reply Go to top Go to top Go to top

Using Annotations to add Validity Constraints to JavaBeans?

Posted by: Brian Miller on March 21, 2005 in response to Message #162385
In *real word* applications validations done using data in database. So IMHO this is very limited.

I agree that DB constraints are great. Constraints should be declarative when possible. Annotations are consistent with that.

Of course the JRE has had extremely rich declared constraints for some time now, in the form of JAXB-bound XML Schema. A POJO/JAXB binding readily obviates custom constraint logic. Custom procedural validation should be a last resort. A benefit of annotations is not needing an external schema. Though an external schema could easily be transformed into annotations.

Eiffel Design-By-Contract assertions are finally in reach. Ie pre/post/conditions and invariants. So the quality of Java programs goes up a notch.

  Message #162637 Post reply Post reply Post reply Go to top Go to top Go to top

We have to distinguish between the use cases of validation

Posted by: Brian Miller on March 21, 2005 in response to Message #162414
Yes having constraint validation is very important but in general we should distinguish between “syntactic” validation and business logic validation.

Presumably constraint annotations would allow arbitrary expressions, in which case semantic validation is treated the same as syntatic validation.
Usually the earlier we can apply this validations the better it is.

...which is a reason why DB constraints are insufficient.
One should also consider that detecting a constraint validation at some random point in the execution stack is futile.

Effeil invariants contradict your claim.

  Message #162641 Post reply Post reply Post reply Go to top Go to top Go to top

Reinventing the past

Posted by: Sony Mathew on March 21, 2005 in response to Message #162584
Annotations are elegant and the runtime introspection is definitely a good point for annotations but ....

But here - we need to create all the Annotation classes - which is essentially the same as Java code, and then a Decorator around the Address class to do the validation based on reading at runtime the constraint annotations. Doesn't this seem like a lot of trouble and less clear ???

Its seems a lot simpler and clearer to just do this ...

public void setStreet(String street) {
  checkStreet(street);
  this.street = street;
}

private void checkStreet(String street) {
  Constraint.checkNotNull(string);
  Constraint.checkLength(10, 20);
}

Its clear, its OO refactorable to give you all the reuse you want. There is no runtime introspection - which has atleast one good point -> its faster.

I don't think Annotations should be used where there is no container providing some specific service for the application - like a runtime mapping to a database or transaction, security etc. type management. If we have to write the annotations and then then define their types and their implementations - how is that different from writing it in Java ?

Maybe a Constraint-Container would give some validity to this article .... Open Source folks .... ???

  Message #162646 Post reply Post reply Post reply Go to top Go to top Go to top

Reinventing the past

Posted by: Jacob Hookom on March 21, 2005 in response to Message #162641
I don't think Annotations should be used where there is no container providing some specific service for the application - like a runtime mapping to a database or transaction, security etc. type management. If we have to write the annotations and then then define their types and their implementations - how is that different from writing it in Java ? Maybe a Constraint-Container would give some validity to this article .... Open Source folks .... ???

I believe constraints/annotations should only be asserted based on some container's context-- such as using the bean within a persistence layer or web tier.

http://www.onjava.com/pub/a/onjava/2005/01/19/metadata_validation.html

  Message #162666 Post reply Post reply Post reply Go to top Go to top Go to top

Constraints in the database

Posted by: Jacob Hookom on March 21, 2005 in response to Message #162622
Paolo, Mark, etc,

The approach I'm taking is to use DTOs with Hibernate, and when, for example, I wish to start working with an order, I do:

OrderHeader hdr = hdrDao.find(id);
OrderSession session = new OrderSession(hdr);

session.getExtendedTotal();
session.validate();

hdrDao.store(session.getHeader());

OrderSession follows Sun's Core J2EE patterns' Business Object where state is delegated/encapsulated so the application operates on a Domain. OrderSession itself doesn't have any state other than state that supports the application flow, such as caching.

You possibly hinted that this approach didn't work for you-- can you please elaborate? I've read Fowler's books/site and actually found Domain models to be be a pain to work with since we ended up duplicating a lot of persistence logic instead of delegating it to a DTO that can be used by any Business Object.

The other reason is that to use these persistence frameworks, such as Hibernate, you basically need to provide a getter/setter for every field which, to me, seems more anemic than encapsulating/delegating to a purely stateful DTO.

Any comments would be greatly apprechiated, cheers!

  Message #162689 Post reply Post reply Post reply Go to top Go to top Go to top

Constraints in the database

Posted by: Mark Nuttall on March 21, 2005 in response to Message #162666
Jacob,
 I'm not sure we are refering to the same thing when we say DTO. A DTO is nothing more than private fields and accessors. Anything more, it isn't a DTO (or VO). Is that what you mean as a DTO?

 You don't need to provide accessors with Hibernate. I don't think you do with JDO either. Steve Z?

 I've not fully investigated Sun's patterns, but some of the patterns I have seen (not just from Sun) are not very OO and are not really that good to implement and are really an attempt to solve bad technologies or bad uses of them.

  Message #162693 Post reply Post reply Post reply Go to top Go to top Go to top

Constraints in the database

Posted by: Jacob Hookom on March 22, 2005 in response to Message #162689
Mark, thanks for your comments...

The DTO's I have are 1:1 mappings with the table columns (w/ UserTypes for things such as Money Objects). They have private vars and getters/setters.

http://www.corej2eepatterns.com/Patterns2ndEd/BusinessObject.htm

OrderDTO dto = session.get(OrderDTO.class, id);
OrderSession order = new OrderSession(dto);
order.getTotal();

// auto generate select properties
// i want to expose to other code participating
// in ordering
public OrderSession implements Serializable {
protected final OrderDTO data;
public OrderSession(OrderDTO data) {
   this.data = data;
}
public Money getTotal() {
  return this.data.getTotal();
}
public boolean isValid() {
  // buisiness rules operate on data
}
public OrderDTO getData() {
   return this.data;
}
}

  Message #162703 Post reply Post reply Post reply Go to top Go to top Go to top

Constraints in the database

Posted by: Radu-Adrian Popescu on March 22, 2005 in response to Message #162689
I've actually scrapped the accessors altogether, it's such a built-up concept if the object is really POD.

Regarding Sun's "patterns" (quotes intended) whenever I remember Fast Lane Reader someone has to pick me up off the floor, throw buckets of water etc. Cheesus !

  Message #162704 Post reply Post reply Post reply Go to top Go to top Go to top

Constraints in the database

Posted by: Jacob Hookom on March 22, 2005 in response to Message #162703
I've actually scrapped the accessors altogether, it's such a built-up concept if the object is really POD.Regarding Sun's "patterns" (quotes intended) whenever I remember Fast Lane Reader someone has to pick me up off the floor, throw buckets of water etc. Cheesus !

Lets say that you need to capture and work with some state from the database. At the same time, you only want to expose very little to other code in the application-- encapsulation.

Are you saying that you wouldn't encapsulate/delegate to a separate object that's representative of the database's state?

  Message #162707 Post reply Post reply Post reply Go to top Go to top Go to top

Constraints in the database

Posted by: Radu-Adrian Popescu on March 22, 2005 in response to Message #162704
That's not the point I was trying to make.
PODs (POJOs, though not as correct) are just that, structs. I cannot pretend to hide anything from anyone when it comes to say a Customer's names. What I can do on the other hand is have a CustomerManager or CustomerService that can offer services related to the Customer to other layers and/or clients [of the service]. It would for instance erase email and password information when returning a list of Customers as a search result for a query performed by an user (i.e. real person), or build a custom data structure based on several PODs and so on.
So to answer your question - no, the PODs/DTOs/VOs do not need accessors, they don't do validation nor apply business rules and the like. They're exactly like C structs - and without function pointers.
At the same time domain concerns (i.e. partitioning the domain into problems that need solving, much like services we have to offer to other parties - including ourselves) take care of all the business needs and that also provides encapsulation both as a goal (i.e. imposed by business rules) and as a side-effect (clearly defined interface for interacting with that domain "parcel").

  Message #162712 Post reply Post reply Post reply Go to top Go to top Go to top

Constraints in the database

Posted by: Paolo Guccione on March 22, 2005 in response to Message #162704
I've actually scrapped the accessors altogether, it's such a built-up concept if the object is really POD.Regarding Sun's "patterns" (quotes intended) whenever I remember Fast Lane Reader someone has to pick me up off the floor, throw buckets of water etc. Cheesus !
Lets say that you need to capture and work with some state from the database. At the same time, you only want to expose very little to other code in the application-- encapsulation.Are you saying that you wouldn't encapsulate/delegate to a separate object that's representative of the database's state?

Not writing accessors is one approach. Hibernate allows it easily. I prefer to have the IDE write them automatically, though.

Jacob: wait a minute (Browsing Crupi's Pattern Catalog). Okay, the book actually says that DTOs are about data encapsulation. I would rather say data packaging. Real encapsulation is another story, which is possible only with a non-anemic model.

Whenever the responsibility for managing the object state, such as enforcing data constraints [brief attempt to return on-topic], you are breaking the encapsulation rules, not enforcing them. An encapsulated object is responsible for managing its internal state, not only for storing it.

You can package data even with C or CORBA structs. Does C allow encapsulation IYO ?

A domain object is really encapsulated, because it contains the entity behaviour, too.

I have used the approach you suggested, sure. For each entity (table) you usually end up with: OrderDTO, OrderEJB (EntityBean), OrderDTOAssembler, OrderManager (SessionBean), OrderBusinessDelegate, OrderHelper (just to externalize more behavior).

In the RL example i gave before we also had OrderConverters (Domain-to-DTO and DTO-to-Struts). Anyone interested in knowing the number of developed / auto-generated classes when we were at approx. 20% of the project with a mere four developers? Hundreds.

People, is this what you would call maintainable code?

  Message #162720 Post reply Post reply Post reply Go to top Go to top Go to top

Reinventing the past

Posted by: Stephan Albers on March 22, 2005 in response to Message #162641
Annotations are elegant and the runtime introspection is definitely a good point ..
Its seems a lot simpler and clearer to just do this

...public void setStreet(String street) {&nbsp;&nbsp;checkStreet(street);&nbsp;&nbsp;this.street = street;}private void checkStreet(String street) {&nbsp;&nbsp;Constraint.checkNotNull(string);&nbsp;&nbsp;Constraint.checkLength(10, 20);}

Introspection/Annotations = Meta Data usable at runtime, compile time, deployment time...

In your Java code, you would have the validations available only for the objects/POJOs. But since it's not meta data, you couldn't reuse it to

- create validated DB-schemas (triggers..)
- create HTML forms with Javascript that does client based validation
- create import tools to load verified data from external sources...

I don't think Annotations should be used where there is no container providing some specific service for the application - like a runtime mapping to a database or transaction, security etc. type management.

That is one very important aspect, but the core is that annotations are meta data that can be used at different points in time (compile time, runtime, deployment).

If we have to write the annotations and then then define their types and their implementations - how is that different from writing it in Java ?

You would be right, if this information would only be needed once, but it is potentially needed in many situations (DB, Form, POJO, Load..).

Its clear, its OO refactorable to give you all the reuse you want. There is no runtime introspection - which has atleast one good point -> its faster.

BTW: introspection is very fast compared with DB operations, client interaction.., so that is not important in nearly all situations.

Stephan

  Message #162745 Post reply Post reply Post reply Go to top Go to top Go to top

constaint and design by contract

Posted by: Michel Rondeau on March 22, 2005 in response to Message #162720
It could be interesting to consider the merger of anotations as presented here and Design by Contract (see Java RFC 4449384: http://bugs.sun.com/bugdatabase/view_bug.do?bug_id=4449383). Design by Contact(DbC) specifies that anotations might be validate prior to public call (pre-condition), on return (post-condition) or both (invariant).
Also interesting is the fact that this implementation would be pretty close to has been implemented in iContract (see: http://www.javaworld.com/javaworld/jw-02-2001/jw-0216-cooltools.html).

However, here are the interesting aspects I'd liked to point at:
- DbC specifies that anotations should be part of inheritance (which makes sens as you don't want hers to brake parents behavior);
- anotation might implies that contraints could be specifiy at the property level and apply by getters and setters.

  Message #162747 Post reply Post reply Post reply Go to top Go to top Go to top

Constraints in the database

Posted by: Mark Nuttall on March 22, 2005 in response to Message #162712
People, is this what you would call maintainable code?
Not no, but heck no. Even a Struts app by itself has enough classes. I can only imagine.

  Message #162748 Post reply Post reply Post reply Go to top Go to top Go to top

Files, files

Posted by: Radu-Adrian Popescu on March 22, 2005 in response to Message #162747
People, is this what you would call maintainable code?
Not no, but heck no. Even a Struts app by itself has enough classes. I can only imagine.
Precisely why I never attempted to use Struts. Too many fucking classes and files and shit for what? A shitty web front-end? No fucking way mate.

  Message #162751 Post reply Post reply Post reply Go to top Go to top Go to top

Files, files

Posted by: Mark Nuttall on March 22, 2005 in response to Message #162748
A shitty web front-end?
Isn't that redundant? I looked up
A shitty front-end?
in the dictionary and it said a web UI

  Message #162767 Post reply Post reply Post reply Go to top Go to top Go to top

Reinventing the past

Posted by: Jason Carreira on March 22, 2005 in response to Message #162641
The problem with Annotation or any code-based validation is CONTEXT. Do your objects always validate the same, no matter what context they're in? Well, lucky you, but that's often not the case. When I was designing the XWork Validation Framework, which is XML metadata driven, this was one of the major concerns. The XWork Validation Framework allows you to define validations for different contexts in different XML files:

MyAction-validation.xml -> default validations
MyAction-context1-validation.xml -> validations specific for context1 are added to the defaults
MyAction-context2-validation.xml -> validations specific for context2,....


This allows a lot of flexibility in validating objects differently based on where you are and what you're doing. Being able to use OGNL for expression validations is pretty powerful too...


Annotations are elegant and the runtime introspection is definitely a good point for annotations but .... But here - we need to create all the Annotation classes - which is essentially the same as Java code, and then a Decorator around the Address class to do the validation based on reading at runtime the constraint annotations. Doesn't this seem like a lot of trouble and less clear ??? Its seems a lot simpler and clearer to just do this ...public void setStreet(String street) {&nbsp;&nbsp;checkStreet(street);&nbsp;&nbsp;this.street = street;}private void checkStreet(String street) {&nbsp;&nbsp;Constraint.checkNotNull(string);&nbsp;&nbsp;Constraint.checkLength(10, 20);}

Sorry Sony, but this is horrible... What if this was a password field and its validation depended on the value of password2 (to make sure they're equal)? Per-property validations like this can't get the big picture because you don't know what other dependent properties have been set... Also, sometimes you're creating a new user and you want to check the 2 passwords, and sometimes you're editing an existing user and you don't want to make them enter the password again... Context is king.
Its clear, its OO refactorable to give you all the reuse you want. There is no runtime introspection - which has atleast one good point -> its faster.I don't think Annotations should be used where there is no container providing some specific service for the application - like a runtime mapping to a database or transaction, security etc. type management. If we have to write the annotations and then then define their types and their implementations - how is that different from writing it in Java ? Maybe a Constraint-Container would give some validity to this article .... Open Source folks .... ???

Umm... this is what an IoC container gives you... I know you're not a fan, but Spring can use annotations (or commons-annotations, which I like very much) as the pointcuts to apply AOP to your classes. It's very much declarative programming where you just specify some metadata about your Class and Spring picks it up to provide the right services transparently.

  Message #162784 Post reply Post reply Post reply Go to top Go to top Go to top

Constraints in the database

Posted by: Jacob Hookom on March 22, 2005 in response to Message #162712
For each entity (table) you usually end up with: OrderDTO, OrderEJB (EntityBean), OrderDTOAssembler, OrderManager (SessionBean), OrderBusinessDelegate, OrderHelper (just to externalize more behavior).In the RL example i gave before we also had OrderConverters (Domain-to-DTO and DTO-to-Struts). Anyone interested in knowing the number of developed / auto-generated classes when we were at approx. 20% of the project with a mere four developers? Hundreds.People, is this what you would call maintainable code?

Within the app I'm writing, I just have OrderDTO and OrderSession. The point of doing so is that other code can capture and work with the raw state of the DB (OrderDTO) without instantiating or having to work with the overhead included with OrderSession-- its constraints, events, etc.

Now the DTO's I created are considered anemic, but also provide derived state, behavior that is intrinsic ONLY to the specific DTO-- meaining, a ProductDTO has a derived property 'isStocked' where it checks the state that is available to it and returns a boolean without needing to access any extrinsic knowledge.

I've used the domain pattern on our last application, but consequently, ended up with a bunch of specialized OrderAssembler, OrderManager, OrderService, OrderDelegate-- now multiply that by each behavioral variation in the domain model for Objects that basically work off of the same data (PurchaseOrders, PurchaseLists, VendorQuotes, ConfirmedOrders, etc). Each variation has its own behavior and must be exposed/instantiated through its own set of supporting services/managers/assemblers. Granted there was some abstraction used, but the point is that I ended up with tons of objects AND interfaces to support each domain object we concieved.

A better solution, IMHO, is that you separate persistence/state from behavior-- such that you only have a single OrderDTO and ONE set of services supporting that DTO and persistence logic. When you need to introduce behavior and constraints anywhere in the system, you simply wrap the DTO and go--

  Message #162842 Post reply Post reply Post reply Go to top Go to top Go to top

declarative constraints == separation of concerns

Posted by: Bill Schneider on March 22, 2005 in response to Message #162381
I think declarative constraints are a great idea, because it separates the actual constraints from the implementation used for enforcing them.

If I have something like

@MaxLength(40)
String name;

... I can use the same "@MaxLength(40)" annotation to drive web UI validation (e.g., ActionForm), SOAP request validation, WSDL/XSD generation, DB schema generation, even HTML forms themselves (<input maxlength=...>)

Otherwise, there's a lot of cut-and-paste for all the references where I need to know that a particular field is 40 chars long.

  Message #162877 Post reply Post reply Post reply Go to top Go to top Go to top

Constraints in the database

Posted by: Sony Mathew on March 22, 2005 in response to Message #162666
I have tried this approach. Its nice but tedious when attempting to wrap all your data objects with a rich object - especially when dealing with entity relationships - where each rich wrapper is now responsible for creating a wrapper around a collection of its related entities - but one can choose to avoid this problem i.e. rich wrappers don't manage relationships but this pushes even more tediousness to the usecase controller.

Have others had similar issues ?

  Message #162878 Post reply Post reply Post reply Go to top Go to top Go to top

Reinventing the past

Posted by: Sony Mathew on March 22, 2005 in response to Message #162767
The context in this case is limited to the street property within the address object who is essentially the controller for this context. Every context has a controller - and so a larger scoped context and its validation will be managed by an equivalent larger controller. E.g. a usecase and its specific validations would be managed by a larger usecase controller.

The validation depicted in the author's (and my) example is merely a constraint on the street restricted to the scope of an Address object's context.

The validations of a larger context and its controller can be OO refactored for reuse just like the validations of a smaller context as I depicted.

As a rule of thumb one would never squeeze the logic of a larger context into a smaller one - a clear design flaw.

P.S I am not against Containers that provide useful services using Annotations or even XML based meta data including the services you suggest. I just don't see why IOC needs to be container managed - especially managing an entire object model relationship. IOC should be a standalone pattern just as any other pattern.

  Message #162887 Post reply Post reply Post reply Go to top Go to top Go to top

Constraints in the database

Posted by: Radu-Adrian Popescu on March 23, 2005 in response to Message #162877
have tried this approach. Its nice but tedious when attempting to wrap all your data objects with a rich object
I've not tried it in practice but have read code that does and have thought about how things would look if I had - not a pretty sight. I prefer the service-per-domain-problem approach. These start at a coarse-grained level and use database-based DTOs as input/output data at first. As business requirements distill problem-oriented services are refactored, new service-speciffic (non-db based) DTOs are added to refine the existing ones, and even services are split up or re-combined.
For instance here's how an instant messaging server would look: UserService, ChatService, SearchService. DTOs would be something like User, ChatMessage etc. As needs refine services are added, split or recombined. Also new DTOs are likely to appear, either database-based or not, for instance a List<User> initially serving as a search result might be changed to List<SearchResult> later on if we decide that we should search both users and archived conversations together (it's a rather stupid example indeed).
The service implementations go about their thing in resolving the domain problems at hand. They can have global state or not. They manage database transactions themselves, delegate complex logic to specialised business "sub-services"; for instance if you could play hang-man with the server in a chat session this would not be implemented directly in the chat service, but as a layer, as a mix-in. Basically the front services coordinate transactions and agregate business logic, maintain state (if they're not stateless) and provide flow control, in terms of (message received) -> (begin) -> [delegate: offensive_words_filtering_subservice] -> [delegate_if_required: text_games_subservice] -> (persist) -> (commit) -> (notify) -> (ack). Or something like that.

So, what do you guys think ?

  Message #162977 Post reply Post reply Post reply Go to top Go to top Go to top

Constraints in the database

Posted by: Jacob Hookom on March 23, 2005 in response to Message #162877
I have tried this approach. Its nice but tedious when attempting to wrap all your data objects with a rich object - especially when dealing with entity relationships - where each rich wrapper is now responsible for creating a wrapper around a collection of its related entities - but one can choose to avoid this problem i.e. rich wrappers don't manage relationships but this pushes even more tediousness to the usecase controller. Have others had similar issues ?

It's not that difficult when you say that your rich object only deals with rich objects-- so you have:

// pulling up an order to work with it
HeaderDTO hdr = hdrService.find(id);
List<DetailDTO> dtls = dtlService.find(id);

List<OrderLine> lines = OrderLine.wrap(dtls);
Order order = new Order(hdr, lines);

// work with order, adding a new line item
Product prd = prdService.find(id);

DetailDTO dtl = new DetailDTO(order.getHeader());
dtl.assignProduct(prd);
dtl.setQuantity(qty);
dtlService.insert(dtl);

order.getLines().add(new OrderLine(dtl));

// done.

  Message #162985 Post reply Post reply Post reply Go to top Go to top Go to top

Constraints in the database

Posted by: Jacob Hookom on March 23, 2005 in response to Message #162576
http://www.javadude.com/articles/

I read that article and found it to be utter crap. Contract based design, especially by interfaces, only provides unecessary complexity. The author of the article says 'Interfaces are the Key', well interfaces ARE NOT LAYERS.

If within my application, I have an Object representative of an Order in the database... what do I gain by putting an interface in front of it? If the database changes, both the interface AND the implementations will have to change with it.

The number one tool in maintaining applications and easing others understanding of your code is being able to right click in the code and 'go to declaration'. If every time someone goes to a Domain Object's definition, they end up at an interface-- boy that's going to get annoying after a while. This is why I'm opting instead to create layers through delegation instead of interfaces. Hence my use of DTO's that are wrapped by BusinessObjects.

  Message #162993 Post reply Post reply Post reply Go to top Go to top Go to top

Constraints in the database

Posted by: Paolo Guccione on March 23, 2005 in response to Message #162985
First of all I suggest that everyone in this thread read also the "Using annotations to replace getters/setters" thread, just a few lines above. Not everybody agreed with the article (including Cameron Purdy) but I tend to share much of the author's PoV.

Perhaps we should also move this discussion to that thread, in an unusual attempt to remain on-topic.
I read that article and found it to be utter crap. Contract based design, especially by interfaces, only provides unecessary complexity. The author of the article says 'Interfaces are the Key', well interfaces ARE NOT LAYERS.

Interfaces help define layers by allowing a layer to describe itself to other layers without exposing their implementation details. Without interfaces, layers would be tightly coupled, and this would nullify their usefulness. Coupled layers == useless complexity. Layers decoupled through interfaces == a system that tolerates requirement changes.
If within my application, I have an Object representative of an Order in the database... what do I gain by putting an interface in front of it? If the database changes, both the interface AND the implementations will have to change with it.

Only if you have tightly coupled the user interface and the database (like in ol' good CRUD-based COBOL screen maps). The interface and implementation MUST change if user requirements change, not necessarily when the schema does. And do not tell me that you implement user requirements in the database.

One of the key principles in a good J2EE architecture is "Do not make the application logic dependent on the DB schema". Perhaps this is the point you missed?
This is why I'm opting instead to create layers through delegation instead of interfaces. Hence my use of DTO's that are wrapped by BusinessObjects.

Ahem, if you read Gamma et al. [GoF], it clearly states that "Extension by delegation" is the key to a maintainable design, sure. The problem is that the book clearly states (read the other thread, too) that interfaces are the key to delegation and decoration. Delegator and delegated object must implement the same interface (extend the same abstract class in C++ - a very abstract class), or you end up with a mess of non-replaceable components. Are you wishing to contradict Gamma ? Though everybody should be free to contradict anybody, I suppose you must have a very strong point in order to do so and not lose credibilty.

  Message #162997 Post reply Post reply Post reply Go to top Go to top Go to top

Constraints in the database

Posted by: Mark Nuttall on March 23, 2005 in response to Message #162993
Thanks Paulo,
 I just sat there flabbergasted not sure where to start replying.

 As for being able to go to the concrete class - if one is using Eclipse - Ctrl + T. Pretty easy and pretty cool. Doing it right (using Interfaces) use to be a pain but the Java IDEs have made it pretty simple (.Net on the other hand ... :( ).

  Message #163006 Post reply Post reply Post reply Go to top Go to top Go to top

Constraints in the database

Posted by: Jacob Hookom on March 23, 2005 in response to Message #162993
Only if you have tightly coupled the user interface and the database (like in ol' good CRUD-based COBOL screen maps). The interface and implementation MUST change if user requirements change, not necessarily when the schema does. And do not tell me that you implement user requirements in the database. One of the key principles in a good J2EE architecture is "Do not make the application logic dependent on the DB schema". Perhaps this is the point you missed?

Maybe it's the fact that I spend my time designing enterprise systems for a fortune 25 medical supplier-- but trying to build up useless layers on top of the db, instead of treating it as part of your application, is a waste of time and processing power and only adds useless complexity.

This is why I've chosen the route of having a literal mapping of DTO's to database tables. Services are built upon the DTO's and their relationships-- no application requirements or logic introduced at this point.

When one of our many applications now needs to work with that data, they just wrap the DTO returned from a DTO Service with a Business Object (introducing another layer) that the client application interacts with.
Ahem, if you read Gamma et al. [GoF], it clearly states that "Extension by delegation" is the key to a maintainable design, sure. The problem is that the book clearly states (read the other thread, too) that interfaces are the key to delegation and decoration. Delegator and delegated object must implement the same interface (extend the same abstract class in C++ - a very abstract class), or you end up with a mess of non-replaceable components. Are you wishing to contradict Gamma ? Though everybody should be free to contradict anybody, I suppose you must have a very strong point in order to do so and not lose credibilty.

GoF is a library of suggested patterns that should not be applied in all cases. If I was writing a public framework, then yes, I would use interfaces with the delegates. But we are talking about writing business applications where higher layers are built upon lower layers-- correct?

So, if lower layers change, such as the DB schema, *some* chages will perculate up through the layers. Putting an interface in front of that object isn't going to gain you anything over a straight object.

Example, we add an email field to an order header. In my system, you only need to add that field to the one DTO representative of that header. No changing multiple interfaces, or layers. Any objects that use that DTO immediately have that field available now to them and if they in turn want to expose it, they can just right click on the internal reference and 'generate delegate methods'. Done.

Interfaces should only be introduced only when you need to provide MULTIPLE implementations. Trust me, I know what I'm talking about-- I had previously written an large application that basically followed that JavaDude article to a T, it's a pain in the ass to maintain changes. I'm much smarter and wiser now :-)

  Message #163013 Post reply Post reply Post reply Go to top Go to top Go to top

Constraints in the database

Posted by: Jacob Hookom on March 23, 2005 in response to Message #162997
Thanks Paulo,&nbsp;I just sat there flabbergasted not sure where to start replying.&nbsp;As for being able to go to the concrete class - if one is using Eclipse - Ctrl + T. Pretty easy and pretty cool. Doing it right (using Interfaces) use to be a pain but the Java IDEs have made it pretty simple (.Net on the other hand ... :( ).

What it comes down to with developing business applications, is that with layering, changes will eventually occur, and when they do-- how many hurdles do you want to have thrown in your way?

Either you accept the database for what it is up front, or you can spend your initial development and the lifetime of the application fighting it. The same goes for any other system or concern within your application. Putting interfaces in front of it isn't going to gain you anything. They are what they are and seek out other OO principals that are more efficient at covering your ass such as-- the Single Responsibility Principle, Liskov Substitution Principle, and Delegation and Composition.

  Message #163102 Post reply Post reply Post reply Go to top Go to top Go to top

Constraints in the database

Posted by: Paolo Guccione on March 24, 2005 in response to Message #163006
GoF is a library of suggested patterns that should not be applied in all cases.

The "interfaces are the key" principle that I quoted is not in a particular pattern description but in the introduction part, which is the best collection of OO methodology advice written so far. Besides, you are stating that your architecture is built on the Decorator (Delegator) pattern, so you are in fact using one GoF pattern intensively (who doesn't?). My question, which received no answer, was, to be more explicit, "Do you think you know better than Mr. Gamma how the Decorator pattern is to be implemented?". A "yes" answer would be, of course, unquestionable.

<blockqote>No changing multiple interfaces, or layers.
The point is that you should not use multiple interfaces but multiple implementations at most. You use one interface (that may or may not map the DB schema on a 1-1 basis), and each layer can provide a different implementation, or use the common one. When one layer changes, changes do not necessarily propagate to the other layers. It is only the local implementation that changes, not the interface. And in simple situations all layers can use the same DTO or domain object. With your solution all layers must use the same implementation.
Interfaces should only be introduced only when you need to provide MULTIPLE implementations.

Since you cannot tell in the beginning whether the requirement for multiple implementations will eventually arise, at least in a non-trivial system, it is clear that interfaces are always needed if you want your system to be ready to accept requirement changes.

Ok, from now on let's move this to another thread more related to the topic. Or better stop it altogether, since the debate is on the verge of entering the domain of impoliteness.

  Message #163252 Post reply Post reply Post reply Go to top Go to top Go to top

Constraints in the database

Posted by: Radu-Adrian Popescu on March 24, 2005 in response to Message #163006
but trying to build up useless layers on top of the db, instead of treating it as part of your application, is a waste of time and processing power and only adds useless complexity.

I second that. Overdesign is a menace.
The data and the database are an integral part of the application. It's pointless to have anything more than a Facade in front of it, except for DTOs and (maybe) DTO service. I think the DTO service objects as Jacob calls them, or Domain Objects as other do are really necessary only when there's a certain level of richness and expresivity intrinsic to the data. From a design point of view I've seldom found this is the case, or simply preffered to go another route and instead build small problem-oriented service cores.
For instance instead of having an AccountDTOBusinessObjectOrServiceOrDomainModelObjectOverAnAccount that handles currency exchange rates and conversions and fees I've chosen to implement the required operations as a small FeeService that uses the DTOs Account, CurrencyExchange and Fee to provide required transformations, skew exchange rates, compute profit and so on. This service core is used in the user-facing (where user is another application using the system) AccountService, that on a higher level provides operations such as transfer, getting the balance and so on, without exposing the intricacies of the currency-related code.
In this scenario it does not make much sense to have speciffic objects ontop of each DTO, since for example the currency exchange and fee/profit thing does not belong anywhere. Also I do preffer having transaction code in a single unit of processing, not split at different depths in the layering.

  Message #163254 Post reply Post reply Post reply Go to top Go to top Go to top

Constraints in the database

Posted by: Radu-Adrian Popescu on March 24, 2005 in response to Message #163102
Since you cannot tell in the beginning whether the requirement for multiple implementations will eventually arise, at least in a non-trivial system, it is clear that interfaces are always needed if you want your system to be ready to accept requirement changes.

I think that on the contrary and in respect to the DTO + database issue, i.e. data changes, the need for multiple implementations is really not there. I mean fair enough, SAP runs on several databases, but most enterprise apps don't just change or swap that part.
The need for interfaces arises at other levels in my oppinion. For instance you may want to replace the entire authentication layer, or add more implementations thereof. Services are definitely canditates for abstraction and formalisation.

  Message #167649 Post reply Post reply Post reply Go to top Go to top Go to top

files, files - finally it is said

Posted by: Matthew Pope on April 23, 2005 in response to Message #162748
Model, View, Controller
Smalltalk got it right. Why can't Java?
Was Oak really that busted that Sun's engineers had not the design room to ensure the fundemental MVC architecture of Smalltalk was built into Java?

The virtual machine design is based on Smalltalk. Why are we having to add MVC as design-pattern to our apps? Why the large extra namespace of Struts for a basic, fundemental archtectural underpinning that all OO applications require?
 
Smalltalk was invented in 1971 at Xerox Parc, Goldberg et al
It's been 34 years. We have mail, telephony, 2D, 3D, multi-media libs, all part of Java, in the Standard edition, but we lack a transparent, well designed, low namespace MVC solution.

Stewardship means leadership too....
Matthew

New content on TheServerSide.comNew content on TheServerSide.comNew content on TheServerSide.com

Dependency Injection in Java EE 6 - Part 1

Reza Rahman explores the features of the proposed JSR 299, Contexts and Dependency Injection for Java EE (CDI). When approved, it promises to be a key feature of Java EE 6. (November 2, Article)

SAML: It's Not just for Web services

SAML is an XML-based standard for exchanging authentication and authorization data between security domains. The single most important problem that SAML was created to solve is the Web browser Single Sign-On problem. Many organizations are debating whether to stay with version 1.1 or move to 2.0. This article makes observations about both options. (September 28, Article)

Programming is Also Teaching Your Team

Joe Ottinger takes a look at how people learn, and applies it to the practice of programming. He notes that understanding how people learn is an essential part of working in a programming team. (September 22, Article)

Can Java EE Deliver The Asynchronous Web?

Stephen Maryka gave us an article about the Asynchronous Web and posed a number of questions that get examined like an approach to delivering Asynchronous Web capabilities through extensions to existing Java EE technologies. (July 14, Article)

JSF Flex

JavaServer Faces Flex goal is to provide users capability in creating standard Flex components, part of flexSDK which is open sourced through MPL license, as normal JSF components. This article by Ji Hoon Kim will provide an overview of creating a simple multilingual JSF page consisting of JSF Flex tags. (June 29, Article)

The Rules of SOA - A Road to a Successful SOA Implementation

In this session Jeff explores the key characteristics of successful SOA projects. He covers some of the patterns, and anti-patterns, tool sets, and strategies that he himself learned the hard way. Last, he provides a strategy and blueprint for achieving a high likelihood of success in your SOA project. (June 23, Tech Talk)

Ari Zilka Talks About Terracotta 3.1

Ari Zilka, CTO of Terracotta, Inc., talks about the new features in Terracotta 3.1, announced during JavaOne and available now. (June 15, Tech Talk)

Enterprise Application Integration, and Spring

In this Tech Talk, Josh Long explores an integration challenge using Spring Integration and walks through the implementation, employing and expanding on the basic patterns of Enterprise Application Integration to tie together components into a function integration solution, and then demonstrates how Spring Integration helps address the integration requirements. (June 15, Tech Talk)

Google Web Toolkit: An Introduction

In this Tech Talk, David Geary teaches you: The basics of Google Web Toolkit; How to implement Ajax-enabled applications in Java; Internationalization; Hooking into the browser history mechanism; Remote procedure calls. (June 4, Tech Talk)

Just Enough Early Architecture to Guide Development

Jon Kern discusses the best architecture/technical solutions and ensure that they are repeated by all developers. By tackling the architecture up-front in a serial manner, subsequent parallel development will be much more manageable and predictable. (May 28, Tech Talk)

Productive Programmer: On the Lam from the Furniture Police

This keynote describes the frustrations of modern knowledge workers in their quest to actually get some work done, and solutions for how to guard yourself against all those distractions. Neal Ford talks about environments, coding, acceleration, automation, and avoiding repetition as ways to defeat the misguided attempts to sap your ability to produce good work. (May 26, Tech Talk)

Auto-Scaling Your Existing Web Application

Gil demonstrates how new, aggressive uses of already abundant compute capacity by common applications offer competitive value for application designers. (May 21, Tech Talk)

Automating Hibernate Mapping and Queries For Java Web Development

Chris Keene introduces WaveMaker as a new way to automate the ability to generate Hibernate classes in order to more quickly bring OR mapping into an application. (May 19, Article)

Auto-Scaling Your Existing Web Application

In this session Nati Shalom demonstrates how to take a standard Java EE web application and scale it out or down dynamically without changes to the application code. Seeing as most web applications are over-provisioned to meet infrequent peak loads, this is a dramatic change because it enables growing your application as needed, when needed, without paying for unutilized resources. (May 19, Tech Talk)

Free Book PDF Download: Mastering EJB Third Edition

Mastering EJB was one of the original and most influential EJB books in the industry. Mastering EJB III now returns with two new expert co-authors, updated for EJB 2.1 and 30% new chapters including security, integration, best practices, open source, and more.
(Book PDF Download)

Application Server Matrix

The Application Server Matrix is a detailed listing of J2EE vendors and their application server products, with information on latest version numbers, J2EE spec support and licensing, pricing, platform support, and links to product downloads and reviews.
(Application Server Comparison Matrix)

News | Blogs | Discussions | Tech talks | Patterns | Reviews | White Papers | Downloads | Articles | Media kit | About
Java Solutions
All Content Copyright ©2007 TheServerSide Privacy Policy
Site Map