Ibatis ist ein Object-Relational-Mapper der auf einem recht enfachen Ansatz beruht. In einer XML-Konfigurationsdatei werden SQL-Ausdrücke definiert, die auf Objekte gemappt werden. Der Ansatz von Ibatis unterscheidet sich zu Hibernate darin, dass SQL-Ausdrücke grundsätzlich per Hand definiert werden. Bei Hibernate die SQL-Ausdrücke für das reine CRUD-Mapping zwar automatisch generiert, dafür zum Teil umständlich mit Annotations gesteuert werden. Daher entfällt auch eine zusätzliche Skriptsprache wie etwa HQL bei Hibernate, Definitionen werden einheitlich in SQL spezifiziert.
Das Bootsrapping erfolgt durch den SqlMapClientBuilder der mit einer XML-Config-Datei versorgt wird und einen SqlMapClient erzeugt:
InputStream stream = getClass().getResourceAsStream("sql-map-config.xml"); SqlMapClient client = SqlMapClientBuilder.buildSqlMapClient(stream);
Diese Config-Datei kann wir folgt aussehen:
<?xml version="1.0" encoding="UTF-8" ?> <!DOCTYPE sqlMapConfig PUBLIC "-//ibatis.apache.org//DTD SQL Map Config 2.0//EN" "sql-map-config-2.dtd"> <sqlMapConfig> <settings useStatementNamespaces="true"/> <typeHandler javaType="java.net.URI" callback="com.intersult.UriTypeHandler"/> <transactionManager type="JDBC"> <dataSource type="SIMPLE"> <property name="JDBC.Driver" value="com.microsoft.sqlserver.jdbc.SQLServerDriver"/> <property name="JDBC.ConnectionURL" value="jdbc:sqlserver://host:1433;databaseName=database"/> <property name="JDBC.Username" value="username"/> <property name="JDBC.Password" value="password"/> </dataSource> </transactionManager> <sqlMap resource="com/intersult/db/sql-map.xml"/> </sqlMapConfig>
Diese Datei referenziert eine odere mehrere Mapping-Dateien, die mit Namespaces versehen werden können. Darin werden die eigentlichen Mappings definiert:
<?xml version="1.0" encoding="UTF-8"?> <!DOCTYPE sqlMap PUBLIC "-//ibatis.apache.org//DTD SQL Map 2.0//EN" "sql-map-2.dtd"> <sqlMap namespace="test"> <select id="test" resultClass="int"> select 7 </select> </sqlMap>
Aufgerufen wird das ganze aus dem Java-Code dann wie folgt:
Integer result = (Integer)client.queryForObject("test.test");
<resultMap id="user" class="com.intersult.User"> <result column="username" property="username"/> <result column="firstname" property="firstname"/> <result column="name" property="lastname"/> </resultMap>
<iterate property="filters" conjunction="AND"> <iterate property="filters[]" conjunction="OR" open="(" close=")"> $filters[].[].dimension.column$ $filters[].[].operator.operator$ #filters[].[].value# </iterate> </iterate>
Die unterliegende Class sieht dabei wie folgt aus:
public class Filters<D extends Dimension> { public List<List<Filter<D>>> getFilters() { return ...; } }