ActiveJDBC: new Java ORM and an ActiveRecord implementation

This is a guest post by Igor Polevoy (blog, @ipolevoy). Igor is a Chief Architect at Productive Edge, LLC.

When I learned Ruby on Rails, I was first and foremost impressed with ActiveRecord. For those who do not know ActiveRecord, it is a Ruby on Rails’ ORM layer, which is an equivalent to Hibernate in Java. However, ActiveRecord is easier to work with because it is based on conventions rather than configuration, and also it configures itselt at start time based on structure of data in the database. I was so impressed with ActiveRecord, that I was sure someone would implement it in Java, but after waiting a couple of years, I put a stop to wait and implemented it myself (with help of a few friends).

ActiveJDBC is a fast and lightweight library for accessing relational databases. Its syntax is concise and easy to understand. The library is based on following principals:

  • No configuration, just conventions
  • No need to learn another QL – SQL is sufficient
  • Code must be lightweight and intuitive, should read like English
  • No sessions, no “attaching, re-attaching”
  • No persistence managers.
  • No proxying. What you write is what you get (WYWIWYG)

ActiveJDBC has no configuration, it maps models to tables automatically. Here is an example:

public class Person extends Model{
}

This is a fully functioning class for accessing the PEOPLE table. The following code works right out of the box:

List retirees = Person.where("age > ?", age);

Since ActiveJDBC does not introduce a new query language, the snippet “age > ?” is a true SQL snippet which usually follows the “WHERE” clause. ActiveJDBC does not require setter/getter methods for mapping to columns. Instead, it provides a single get and a single set method:

String firstName = person.get("first_name");
person.set("last_name", lastName);

Writing setters and getters is possible for convenience:

public Sting getFirstName(){
   return get("first_name");
}

ActiveJDBC supports three types of relationships: one to many, many to many and polymorphic. In a one to many relationship, many records from a “child” table relate to one record in the parent table. Exampes are: customer and addresses, order and line items, etc. When ActibeJDBC starts up, it undergoes a disovery phase, when it examines database metadata (tables, columns, relationships) and maps model classes to tables. For example, if there is a table CUSTOMERS and a table ADDRESSES, and a table ADDRESSES has a column “CUSTOMER_ID”, then you can write code like this without any additional configuration:

Customer c = Customer.findById(123);
List addresses = c.getAll(Address.class);

Many to many and polymorphic associations are supported similarly. ActiveJDBC is full featured and has been around since 2009. If you are interested to learn more, follow the link to the project site:http://code.google.com/p/activejdbc/


After years of “complicated” enterprise Java, things are starting to improve, one of the main directions in enterprise Java today is to make things simple. I think persistence is still more complicated than it should be. ORM frameworks such as Hibernate or JPA, although very powerful (and appropriate in some projects), are also complicated to understand and learn and don’t always “make your development simpler” (JPA has almost 500 page specification document). ActiveJDBS is very simple and elegant persistence framework. My guess is that more and more projects will consider using simple and elegant persistence solutions such as ActiveJDBS.

13 thoughts on “ActiveJDBC: new Java ORM and an ActiveRecord implementation

  1. Nice!

    Can I build a POJO which’s name refers to an SQL View rather than a database table? I’m not sure this feature is available in ActiveRecord or Hibernate or any other ORM framework but it would be pretty cool!!!

    Regards,
    Nicolas

  2. Hi, does every persistent POJO need to extend a “Model”? If so, I’d say this is a pretty invasive and limiting choice. What about moving the “Model” to an annotation and use AOP (AspectJ) for the persistence functionality?

    Regards,

    Marco

  3. yes, every “model” must extend activejdbc.Model. If you examine the programming style you will see that this is anything but invasive. Adding AOP, configuration, injecting additional functionality and making it heavyweight is the last thing I wanted to do.

    Good old inheritance works just fine.

  4. First this looks very cool.

    JPA provides a lot of features, like transactions, rollbacks. How is that handled in ActiveJDBC.

    How about managing relationships, how is that done?. Like Person.getChildren() returns Set <Person>.

    –G

  5. ActiveJDBC follows a DRY model – whatever is already provided in underlying technologies is not supported. Transactions are supported by JDBC, more on this:
    http://code.google.com/p/activejdbc/wiki/Transactions
    The following relationships are supported:
    One to many, Many to many, as well as polymorphic

    Examples:
    List addresses = user.getAll(Address.class)
    or:
    List shippingAddresses = customer.get(Address.class, “address_type = ?”, “shipping”);

    Table of contents can be found:
    http://code.google.com/p/activejdbc/wiki/Features

  6. No XXX, No YYY, etc etc.
    Sure, but then you have to bastardise your data model to extend this Model. No transparency in that

  7. Pingback: Java Pins
  8. Very nice framework, simple and fast.

    Do you plan to support NoSQL solutions?

    Do you plan to support more simple no-instrumentation version?

    You have good support from DB to java objects, do you support and the other way, if i add new field in entity or new relation, can i easily transfer that to DB?

  9. The majority of the persons who develop with java, they are very complicated, then, when they find a project as this one, they are scared.
    Please, does not exist only java!!!, Read info related with Grails or Ruby, Not everything solves with one million of methods Java, Neil… it is necessary to go out of the box.

    Big Project, I testing this.
    Regards

  10. I have this code :

    Base.open(“com.mysql.jdbc.Driver”, “jdbc:mysql://localhost/griddemo”, “root”, “”);
    User u = User.findById(“1”);
    System.out.println(u.toString());

    When I run I get this:

    Exception in thread “main” org.javalite.activejdbc.DBException: java.lang.RuntimeException: Class org.javalite.activejdbc.Model can not access a member of class activejdbc.User with modifiers “”
    at org.javalite.activejdbc.Model.instance(Model.java:2297)
    at org.javalite.activejdbc.LazyList$1.onNext(LazyList.java:307)
    at org.javalite.activejdbc.RowListenerAdapter.next(RowListenerAdapter.java:29)
    at org.javalite.activejdbc.RowProcessor.processRS(RowProcessor.java:59)
    at org.javalite.activejdbc.RowProcessor.with(RowProcessor.java:39)
    at org.javalite.activejdbc.LazyList.hydrate(LazyList.java:305)
    at org.javalite.activejdbc.LazyList.size(LazyList.java:531)
    at org.javalite.activejdbc.Model.findById(Model.java:1678)
    at activejdbc.User.findById(SimpleExample.java)
    at activejdbc.SimpleExample.main(SimpleExample.java:31)
    Caused by: java.lang.RuntimeException: Class org.javalite.activejdbc.Model can not access a member of class activejdbc.User with modifiers “”
    … 10 more
    Caused by: java.lang.IllegalAccessException: Class org.javalite.activejdbc.Model can not access a member of class activejdbc.User with modifiers “”
    at sun.reflect.Reflection.ensureMemberAccess(Reflection.java:65)
    at java.lang.Class.newInstance0(Class.java:351)
    at java.lang.Class.newInstance(Class.java:310)
    at org.javalite.activejdbc.Model.instance(Model.java:2282)
    … 9 more
    Java Result: 1

    How do I resolve the error:

    JOHN K. NJUE.
    Regards…

Leave a Reply

Fill in your details below or click an icon to log in:

WordPress.com Logo

You are commenting using your WordPress.com account. Log Out / Change )

Twitter picture

You are commenting using your Twitter account. Log Out / Change )

Facebook photo

You are commenting using your Facebook account. Log Out / Change )

Google+ photo

You are commenting using your Google+ account. Log Out / Change )

Connecting to %s