Interesting stuff Daniel! Could you provide more details on how that looked in your Wicket based project? Would a integration project (ActiveObjects Wicket) be an idea?
How about things like first level cache (for efficiency and to detect cycles)? And do you force users to use interfaces or can they use normal classes? And why didn’t you choose for a Entity annotation rather than an interface?
I guess I’ll have to check out the sources myself first, huh?
I would really appreciate additional info for SaveableEntity and for some further features that are inside. Lacking ActiveRecord style ORM on JAVA keep us on Rails. This can direct us back to JAVA. Syntaxt of ActiveObject is amazingly easy to adopt and flexible. What are the planned features you are thinking about. Can you imagine some implementation of migrations for instance?
Pretty Neat stuff… I understand that this is just in 0.3 version, but still, i am not very comfortable with the interface approach, primarily because it is far easier to generate getters and setters from instance variables than to write both getters and setters by hand…
I guess, there should be a better solution for that.
Yeah, I’m planning on writing an article in the near future talking about how I’m using AO within Wicket. Most of my custom code AO-Wicket relates to the fact that Entities aren’t serializable (since they’re just cached database peers) so special care needs to be taken with models and listviews. It’s fairly straightforward stuff, but I’d love to get the integration closer where possible. This is an area where I have interest, but no clear idea as to what form an integration project would take. Maybe I should look at the Wicket-Hibernate project…
Re: interfaces vs classes: Unfortunately, Java interface proxies only work with interfaces, and not with implemented classes. AO does allow for property change listeners (Java Bean Spec). More usefully, it also allows for custom implementations of methods (ala ActiveRecord method overrides), but I’ll freely admit that the syntax is perhaps a little unintuitive.
I thought about using an entity annotation to just tag entity interfaces rather than extending a predefined interface. But by extending Entity, all entities can inherit methods like getID(), setID(int), getTableName(), addPropertyChangeListener(PropertyChangeListener), etc… rather than having to define these methods in every entity interface. SaveableEntity is a better example of this, since it defines a save() method to execute any pending UPDATEs.
@Ganeshji
Yeah, I’ll freely admit that the major downside to ActiveObjects is it still has a lot of boiler-plate (though still less than POJO-based ORMs). Fortunately, writing getter and setter signatures by hand isn’t too terrible. I’d love to cut down on this boiler-plate still further, but unfortunately Java’s inherent limitations prevent us from going as far as an ActiveRecord-style method_missing.
You don’t have to limit yourself using normal normal JDK proxies though. There are plenty of project that use e.g. cglib to create dynamic proxies using byte code manipulation. Amongst others Hibernate and wicket-ioc.
Maybe Databinder (http://databinder.net/site/show/overview) is something to look at when thinking about an integration project. I’m not sure either. But as you’re trying to cut the ammount of code you need to write, it probably should provide some very convenient models and transaction utilities.
Sorry for spamming, but another thing to look at - if you’re interested - is the phonebook example (http://wicket-stuff.svn.sourceforge.net/svnroot/wicket-stuff/trunk/wicket-phonebook). That’s an example project that shows how you *could* use Hibernate, Shades or iBatis with Wicket. And maybe ActiveObjects sometime as well
Drop me a line if you want write access to wicket-stuff.
Well, you’ve got two choices for the example you gave. You can define the database schema attributes to not allow nulls in the houseID field:
public interface Person extends Entity {
// …
@NotNull
public House getHouse();
@NotNull
public void setHouse(House house);
}
Or for a more complex rule, you could use AO implementations, which are definitely weird, but quite powerful. I’ll make sure I cover them in a future post.
@Eelco
I’ll take a look at those wicket sources. Since I’m working on a project using Wicket and ActiveObjects, it’d obviously be nice to make the integration as tight as possible.
I’ll have to look at cglib and similar. I briefly considered byte-code manipulation when designing the framework, but that always required weird hacks like custom classloaders etc… While I don’t have a problem writing framework internals which do weird stuff, I don’t want the API to be too bizarre.
It’s another persistence library with a similar philosophy - zero configuration, no boilerplate code, no administration, etc. I’ve used it a bit in the past, and it’s really quite cool how it magically stores and loads objects without any ugly ORM code or configuration. If you are familiar with it, what would you say are main advantages of ActiveObjects over BeanKeeper?
No, I wasn’t familiar with it actually. It does seem interesting though. My three problems with it just from reading bits of the tutorial:
* Still requires a lot of boiler-plate code (it’s POJO based)
* Has it’s own query syntax (HQL is a big reason I avoid Hibernate)
* Seems to be List based for relations, rather than the more intuitive (and performant) array based
The problem with POJO-based frameworks, beyond the added boiler-plate, is that everything must be eagerly loaded. Basically, you turn every entity retrieval call into a SELECT * Hibernate can get around this with bytecode manipulation, but personally I’m a little leery of letting random frameworks peer into my class internals.
In ActiveObjects, every value is lazy-loaded and cached. So you use a minimal amount of memory for each entity.
*** Still requires a lot of boiler-plate code (it’s POJO based)
I may be misunderstanding something here. In BeanKeeper your class definition would be:
public class Person {
private String firstName;
public String getFirstName() { return firstName; }
public void setFirstName(String firstName) { this.firstName = firstName; }
}
In ActiveObjects your class (interface) definition would be:
public interface Person extends Entity {
public String getFirstName();
public void setFirstName(String firstName);
}
So, by “boilerplate code”, are you referring to the implementation of the getters and setters? I suppose it is a bit of extra code, but at the same time, being able to use POJOs like this gains you a lot of flexibility:
- You can easily add custom code to your getters and setters
- Works well to persist existing/legacy classes
- External users of your entity classes do not have know or care about the persistence manager, they just create and use POJOs like any other object
I suppose the above may just be general benefits of doing things the POJO way. Anyway, for my particular project, the above points were quite important - I’m sure there are cases where they are not as important (e.g. starting a new project from scratch).
*** Has it’s own query syntax (HQL is a big reason I avoid Hibernate)
Doesn’t AO have its own query syntax too? BeanKeeper queries don’t seem all that different from AO queries to me, for example:
manager.find(Person.class, “name LIKE ? OR age > ?”, “Joe”, 9); // AO
store.find(”find person where name LIKE ‘Joe’ OR age > 9″); // BK
*** Seems to be List based for relations, rather than the more intuitive (and performant) array based
BeanKeeper’s lazy lists are actually the primary reason I used the library for a previous project - you can execute queries that return huge lists with very low memory usage. By using the List interface instead of arrays, BeanKeeper can page objects into memory only when they are actually accessed. This sort of feature is really useful for reporting, where you may be dealing with queries that return hundreds of thousands of objects.
BTW, what is the reason that arrays are more intuitive? Doesn’t everyone these days use Collections instead of arrays (unless you’re doing some low-level stuff)? Regarding performance, it seems unlikely that there would be any noticeable difference between using arrays and Lists for an ORM library.
*** In ActiveObjects, every value is lazy-loaded and cached. So you use a minimal amount of memory for each entity.
Agreed, this is a benefit of using an interface and not a POJO. On the other hand, if you do need to access all the data in an object, it is more efficient to do a single SELECT * than to execute many smaller queries. The memory use of a single object does not typically cause too many problems - it’s normally only when you have thousands of objects in memory at the same time, and the BeanKeeper lazy lists address this issue quite well.
I’m definitely looking forward to trying out ActiveObjects soon. I have a few small BeanKeeper test programs, so it’ll be interesting to re-implement them with ActiveObjects and compare the code and results.
Well, I’ll grant you that boiler-plate POJO vs Proxy is probably about equal. I suppose at some minimal level, the compiler still has to be satisfied. And as pointed out earlier, the POJO approach has the major advantage in that all getters and setters can be generated from fields.
AO actually doesn’t have it’s own query syntax. It’s just using PreparedStatement fragments. For the example you gave, the fragment of “query text” is actually concatenated directly into an SQL query, like so: “SELECT id FROM person WHERE ${query_text}”, and then executed with the specified parameters. I didn’t look, does BK actually use PreparedStatements? And if so, how effectively? This is a really important issue, especially for databases like Derby or Oracle which rely heavily on PS and have lousy performance without them.
Point taken on the SELECT * vs lazy load. Actually, it’s possible in AO to do this sort of thing (I added the functionality like two weeks ago, so like most things it isn’t documented yet). The code would look something like this:
manager.find(Person.class, Query.select(”*”).where(”name LIKE ? OR age > ?”, “Joe”, 9));
Query is just a preparedstatement builder class which allows things like: Query.select().where(”name = ?”, “Bill”).limit(5).order(”name̶ => “SELECT id FROM ${table_name} WHERE name = ? ORDER BY name LIMIT 5″. The idea behind it is that it mimics the ActiveRecord find() syntax a bit, through the filter that Java doesn’t have symbols like Ruby.
July 18th, 2007 at 3:19 am
Interesting stuff Daniel! Could you provide more details on how that looked in your Wicket based project? Would a integration project (ActiveObjects Wicket) be an idea?
July 18th, 2007 at 3:34 am
How about things like first level cache (for efficiency and to detect cycles)? And do you force users to use interfaces or can they use normal classes? And why didn’t you choose for a Entity annotation rather than an interface?
I guess I’ll have to check out the sources myself first, huh?
July 18th, 2007 at 4:31 am
I would really appreciate additional info for SaveableEntity and for some further features that are inside. Lacking ActiveRecord style ORM on JAVA keep us on Rails. This can direct us back to JAVA. Syntaxt of ActiveObject is amazingly easy to adopt and flexible. What are the planned features you are thinking about. Can you imagine some implementation of migrations for instance?
Thanks a lot for this project
David
July 18th, 2007 at 11:49 am
Pretty Neat stuff… I understand that this is just in 0.3 version, but still, i am not very comfortable with the interface approach, primarily because it is far easier to generate getters and setters from instance variables than to write both getters and setters by hand…
I guess, there should be a better solution for that.
-Ganesh
July 18th, 2007 at 11:52 am
@Eelco
Yeah, I’m planning on writing an article in the near future talking about how I’m using AO within Wicket. Most of my custom code AO-Wicket relates to the fact that Entities aren’t serializable (since they’re just cached database peers) so special care needs to be taken with models and listviews. It’s fairly straightforward stuff, but I’d love to get the integration closer where possible. This is an area where I have interest, but no clear idea as to what form an integration project would take. Maybe I should look at the Wicket-Hibernate project…
Re: interfaces vs classes: Unfortunately, Java interface proxies only work with interfaces, and not with implemented classes. AO does allow for property change listeners (Java Bean Spec). More usefully, it also allows for custom implementations of methods (ala ActiveRecord method overrides), but I’ll freely admit that the syntax is perhaps a little unintuitive.
I thought about using an entity annotation to just tag entity interfaces rather than extending a predefined interface. But by extending Entity, all entities can inherit methods like getID(), setID(int), getTableName(), addPropertyChangeListener(PropertyChangeListener), etc… rather than having to define these methods in every entity interface. SaveableEntity is a better example of this, since it defines a save() method to execute any pending UPDATEs.
@Ganeshji
Yeah, I’ll freely admit that the major downside to ActiveObjects is it still has a lot of boiler-plate (though still less than POJO-based ORMs). Fortunately, writing getter and setter signatures by hand isn’t too terrible. I’d love to cut down on this boiler-plate still further, but unfortunately Java’s inherent limitations prevent us from going as far as an ActiveRecord-style method_missing.
July 18th, 2007 at 3:17 pm
Where would you code a business rule like “every person must have a house” or “every person must have a name which may not be blank”?
Your api is a way of persisting a set of data transfer objects.
Hibernate allow one to persist a set of domain model objects that contain the system business rules - which is a hudge difference.
July 18th, 2007 at 3:36 pm
You don’t have to limit yourself using normal normal JDK proxies though. There are plenty of project that use e.g. cglib to create dynamic proxies using byte code manipulation. Amongst others Hibernate and wicket-ioc.
July 18th, 2007 at 3:37 pm
Maybe Databinder (http://databinder.net/site/show/overview) is something to look at when thinking about an integration project. I’m not sure either. But as you’re trying to cut the ammount of code you need to write, it probably should provide some very convenient models and transaction utilities.
July 18th, 2007 at 3:43 pm
Sorry for spamming, but another thing to look at - if you’re interested - is the phonebook example (http://wicket-stuff.svn.sourceforge.net/svnroot/wicket-stuff/trunk/wicket-phonebook). That’s an example project that shows how you *could* use Hibernate, Shades or iBatis with Wicket. And maybe ActiveObjects sometime as well
Drop me a line if you want write access to wicket-stuff.
July 18th, 2007 at 3:52 pm
@richard
Well, you’ve got two choices for the example you gave. You can define the database schema attributes to not allow nulls in the houseID field:
public interface Person extends Entity {
// …
@NotNull
public House getHouse();
@NotNull
public void setHouse(House house);
}
Or for a more complex rule, you could use AO implementations, which are definitely weird, but quite powerful. I’ll make sure I cover them in a future post.
@Eelco
I’ll take a look at those wicket sources. Since I’m working on a project using Wicket and ActiveObjects, it’d obviously be nice to make the integration as tight as possible.
I’ll have to look at cglib and similar. I briefly considered byte-code manipulation when designing the framework, but that always required weird hacks like custom classloaders etc… While I don’t have a problem writing framework internals which do weird stuff, I don’t want the API to be too bizarre.
July 19th, 2007 at 12:41 pm
Have you taken a look at BeanKeeper before?
http://www.netmind.hu/persistence/
It’s another persistence library with a similar philosophy - zero configuration, no boilerplate code, no administration, etc. I’ve used it a bit in the past, and it’s really quite cool how it magically stores and loads objects without any ugly ORM code or configuration. If you are familiar with it, what would you say are main advantages of ActiveObjects over BeanKeeper?
July 19th, 2007 at 1:26 pm
@Daniel
No, I wasn’t familiar with it actually. It does seem interesting though. My three problems with it just from reading bits of the tutorial:
* Still requires a lot of boiler-plate code (it’s POJO based)
* Has it’s own query syntax (HQL is a big reason I avoid Hibernate)
* Seems to be List based for relations, rather than the more intuitive (and performant) array based
The problem with POJO-based frameworks, beyond the added boiler-plate, is that everything must be eagerly loaded. Basically, you turn every entity retrieval call into a SELECT * Hibernate can get around this with bytecode manipulation, but personally I’m a little leery of letting random frameworks peer into my class internals.
In ActiveObjects, every value is lazy-loaded and cached. So you use a minimal amount of memory for each entity.
July 19th, 2007 at 4:29 pm
Thanks for the response. Regarding your comments:
*** Still requires a lot of boiler-plate code (it’s POJO based)
I may be misunderstanding something here. In BeanKeeper your class definition would be:
public class Person {
private String firstName;
public String getFirstName() { return firstName; }
public void setFirstName(String firstName) { this.firstName = firstName; }
}
In ActiveObjects your class (interface) definition would be:
public interface Person extends Entity {
public String getFirstName();
public void setFirstName(String firstName);
}
So, by “boilerplate code”, are you referring to the implementation of the getters and setters? I suppose it is a bit of extra code, but at the same time, being able to use POJOs like this gains you a lot of flexibility:
- You can easily add custom code to your getters and setters
- Works well to persist existing/legacy classes
- External users of your entity classes do not have know or care about the persistence manager, they just create and use POJOs like any other object
I suppose the above may just be general benefits of doing things the POJO way. Anyway, for my particular project, the above points were quite important - I’m sure there are cases where they are not as important (e.g. starting a new project from scratch).
*** Has it’s own query syntax (HQL is a big reason I avoid Hibernate)
Doesn’t AO have its own query syntax too? BeanKeeper queries don’t seem all that different from AO queries to me, for example:
manager.find(Person.class, “name LIKE ? OR age > ?”, “Joe”, 9); // AO
store.find(”find person where name LIKE ‘Joe’ OR age > 9″); // BK
*** Seems to be List based for relations, rather than the more intuitive (and performant) array based
BeanKeeper’s lazy lists are actually the primary reason I used the library for a previous project - you can execute queries that return huge lists with very low memory usage. By using the List interface instead of arrays, BeanKeeper can page objects into memory only when they are actually accessed. This sort of feature is really useful for reporting, where you may be dealing with queries that return hundreds of thousands of objects.
BTW, what is the reason that arrays are more intuitive? Doesn’t everyone these days use Collections instead of arrays (unless you’re doing some low-level stuff)? Regarding performance, it seems unlikely that there would be any noticeable difference between using arrays and Lists for an ORM library.
*** In ActiveObjects, every value is lazy-loaded and cached. So you use a minimal amount of memory for each entity.
Agreed, this is a benefit of using an interface and not a POJO. On the other hand, if you do need to access all the data in an object, it is more efficient to do a single SELECT * than to execute many smaller queries. The memory use of a single object does not typically cause too many problems - it’s normally only when you have thousands of objects in memory at the same time, and the BeanKeeper lazy lists address this issue quite well.
I’m definitely looking forward to trying out ActiveObjects soon. I have a few small BeanKeeper test programs, so it’ll be interesting to re-implement them with ActiveObjects and compare the code and results.
July 19th, 2007 at 5:37 pm
Well, I’ll grant you that boiler-plate POJO vs Proxy is probably about equal. I suppose at some minimal level, the compiler still has to be satisfied. And as pointed out earlier, the POJO approach has the major advantage in that all getters and setters can be generated from fields.
AO actually doesn’t have it’s own query syntax. It’s just using PreparedStatement fragments. For the example you gave, the fragment of “query text” is actually concatenated directly into an SQL query, like so: “SELECT id FROM person WHERE ${query_text}”, and then executed with the specified parameters. I didn’t look, does BK actually use PreparedStatements? And if so, how effectively? This is a really important issue, especially for databases like Derby or Oracle which rely heavily on PS and have lousy performance without them.
Point taken on the SELECT * vs lazy load. Actually, it’s possible in AO to do this sort of thing (I added the functionality like two weeks ago, so like most things it isn’t documented yet). The code would look something like this:
manager.find(Person.class, Query.select(”*”).where(”name LIKE ? OR age > ?”, “Joe”, 9));
Query is just a preparedstatement builder class which allows things like: Query.select().where(”name = ?”, “Bill”).limit(5).order(”name̶
=> “SELECT id FROM ${table_name} WHERE name = ? ORDER BY name LIMIT 5″. The idea behind it is that it mimics the ActiveRecord find() syntax a bit, through the filter that Java doesn’t have symbols like Ruby.