i've been tweaking hibernate scala example my previous post experiment interleave hbm.xml mapping information right into your plain old scala object code sort like poor man's annotation, so you can keep your meta information right snug up your properties helps get around scala's current limitations around deep annotations (so heard) here's example defining and using two scala classes -- scalanate.event and scalanate.person, and hibernate-izing them.. package scalanate import scala.xml._ import java.util.date import org.hibernate._ import org.hibernate.cfg._ class event extends hibernate { var id: long = 0l hibernate(<id name="id" column="event_id"> <generator class="native"/> </id>) var title: string = null hibernate(<property name="title"/>) var date: date = null hibernate(<property name="date" type="timestamp" column="event_date"/>) var participants: java.util.set = new java.util.hashset hibernate(<set name="participants" table="person_event" inverse="true"> <key column="event_id"/> <many-to-many column="person_id" class="scalanate.person"/> </set>) override def tostring = "event " + id + " " + title + " " + date hibernateready } class person extends hibernate { var id: long = 0l hibernate(<id name="id" column="person_id"> <generator class="native"/> </id>) var age: int = 0 hibernate(<property name="age"/>) var name: string = null hibernate(<property name="name"/>) var events: java.util.set = new java.util.hashset hibernate(<set name="events" table="person_event"> <key column="person_id"/> <many-to-many column="event_id" class="scalanate.event"/> </set>) override def tostring = "person " + id + " " + name + " " + age hibernateready } magic repeated calls hibernate() and hibernateready(), which together capture xml mapping information hibernate needs fragments xml should familiar anyone who's had sling around hibernate x.hbm.xml mapping file now, we can crank up program and do some entity creation, saving, and querying.. object main { def main(args: array[string]) { println("main: " + args.mkstring(",")); // use throwaway instances force hibernate // configure these classes // new person new event hibernate.config = <hibernate-configuration> <session-factory> <!-- database connection settings --> <property name="connection.driver_class">org.h2.driver</property> <property name="connection.url">jdbc:h2:mem:test_mem</property> <property name="connection.username">admin</property> <property name="connection.password"></property> <property name="dialect">org.hibernate.dialect.h2dialect</property> <property name="current_session_context_class">thread</property> <!-- emit generated sql debugging --> <property name="show_sql">true</property> <!-- auto-drop/recreate schema startup --> <property name="hbm2ddl.auto">create</property> </session-factory> </hibernate-configuration> args(0) match { case "test0" => test0 case "test1" => test1 } } import hibernate.withtxsession def test0 = withtxsession(session => { val e1 = new event e1.title = "hi" e1.date = new date session.save(e1) }) def test1 = { withtxsession(session => { val e1 = new event e1.title = "hi" e1.date = new date session.save(e1) val e2 = new event e2.title = "bye" e2.date = new date session.save(e2) val p1 = new person p1.name = "p1" p1.age = 21 session.save(p1) }) println("test1.a") import scala.collection.jcl.mutableiterator.wrapper withtxsession(session => { val p1 = session.createquery("from person").list.get(0).asinstanceof[person] println(p1) (e <- new wrapper[event](session.createquery("from event").list.iterator)) { p1.events.add(e) e.participants.add(p1) } }) println("test1.b") withtxsession(session => { val p1 = session.createquery("from person").list.get(0).asinstanceof[person] println(p1) println(p1.events) (e <- new wrapper[event](session.createquery("from event").list.iterator)) { println(e) println(e.participants) } }) println("test1.c") } } and, make above work, you'll need these utility helpers object hibernate { lazy val sessionfactory = configuration.buildsessionfactory lazy val configuration = if (config != null) (new configuration).configure(configdoc).adddocument(mappingdoc) else (new configuration).configure.adddocument(mappingdoc) var config: node = null // app can init this, otherwise, uses hibernate.cfg.xml def configdoc = parsedoc(config) def mappingdoc = parsedoc(<hibernate-mapping default-access="field"> {ready.keys.map( cls => { val attrs = ready.getorelse(cls, map.empty) <class name={cls.getname} table={attrs.getorelse("table", tablename(cls.getname))}> {mappings.getorelse(cls, text(""))} </class> } ) } </hibernate-mapping>) def tablename(classname: string) = classname.substring(classname.lastindexof('.') + 1) def withtxsession(f: (session) => any) = { val s = sessionfactory.getcurrentsession val t = s.begintransaction val r = f(s) t.commit r } // --------------------------------- val mappings = new scala.collection.mutable.hashmap[class, nodeseq] val ready = new scala.collection.mutable.hashmap[class, map[string, string]] def mappingappend(cls: class, x: => nodeseq): unit = if (!ready.contains(cls)) mappings += (cls -> nodeseq.fromseq(mappings.getorelse(cls, text("\n")) ++ x)) def mappingready(cls: class, m: => map[string, string]): unit = if (!ready.contains(cls)) ready += (cls -> m) // --------------------------------- lazy val parsedocfactory = javax.xml.parsers.documentbuilderfactory.newinstance def parsedoc(x: node) = { import org.xml.sax.inputsource import java.io.stringreader parsedocfactory.newdocumentbuilder.parse(new inputsource(new stringreader(x.tostring))) } } // --------------------------------- trait hibernate { def hibernate(x: => nodeseq): unit = hibernate.mappingappend(this.getclass, x) def hibernateready: unit = hibernate.mappingready(this.getclass, map.empty) def hibernateready(m: => map[string, string]): unit = hibernate.mappingready(this.getclass, m) } above, you can see hibernate helper singleton object and companion hibernate trait awfully short all, think, quite interesting exercise dsl possibilities scala.
by
dwayneb
2008-01-26 16:42
lang:scala
·
lib:persistence
·
doc:blog
http://scalabase.ning.com/profiles/blog/show?id=1808193%3ABlogPost%3A261
-
cached
-
mail it
-
history