unit testing Cayenne objects

From: Erik Hatcher (eri..hatchersolutions.com)
Date: Tue May 03 2005 - 08:52:43 EDT

  • Next message: Mike Kienenberger: "Re: Tapestry integration options"

    How are folks doing unit testing with Cayenne?

    I should have asked before embarking on it, but I developed a simple
    base class that constructs an in-memory HSQL database and sets up a
    DataContext to it. This works, but my setUp could use some
    improvement to avoid needing a domain node configuration file. I've
    pasted my base class below. Very pleasantly, Cayenne's DbGenerator
    (which I learned of through the <cdbgen> Ant task code; my philosophy
    is that you can learn all you need about Java from Ant in some way!)
    worked wonders!

    I will also need to implement a TestSetup to only have the database
    created one time once I get more test cases in place and the set up
    time becomes too painful.

    I have also pasted one of my prototype test cases below to show you
    what I'm doing and solicit critique.

    Thanks,
         Erik

    abstract public class DbTestCase extends TestCase {
       public void setUp() throws Exception {
         String baseDir = System.getProperty("cayenneConfigBaseDir");

         // liberally borrowed from Cayenne's DbGeneratorTask
         InputSource in = new InputSource(new File(baseDir,
    "CollexDomainMap.map.xml").getAbsolutePath());
         DataMap dataMap = new MapLoader().loadDataMap(in);

         DbGenerator generator = new DbGenerator(new HSQLDBAdapter(),
    dataMap);
         generator.setShouldCreateFKConstraints(true);
         generator.setShouldCreatePKSupport(true);
         generator.setShouldCreateTables(true);
         generator.setShouldDropPKSupport(true);
         generator.setShouldDropTables(true);

         DriverDataSource dataSource = new DriverDataSource(new jdbcDriver
    (), "jdbc:hsqldb:mem:db", "sa", "");

         generator.runGenerator(dataSource);

         // Configure the Cayenne DataContext to use a test-only set up,
    for an in-memory database
         // TODO: create this configuration dynamically rather than
    loading files, as there is duplication with the above
         // setup with the adapter, map file name, and JDBC URL and
    driver.
         FileConfiguration conf = new FileConfiguration("cayenne.xml");
         conf.addFilesystemPath(new File(baseDir, "test/"));
         conf.addFilesystemPath(new File(baseDir));
         Configuration.initializeSharedConfiguration(conf);

         // Put the data context into a ThreadLocal just like the web
    tier listener does, giving
         // direct DB access to any code that needs it.
         DataContext context = DataContext.createDataContext();
         DataContext.bindThreadDataContext(context);
       }

       protected final DataContext getDataContext() {
         return DataContext.getThreadDataContext();
       }
    }

    public class UserTest extends DbTestCase {

       public void setUp() throws Exception {
         super.setUp();

         User user = (User) getDataContext().createAndRegisterNewObject
    (User.class);
         user.setUsername("validuser");
         user.setPassword("password");
         getDataContext().commitChanges();
       }

       public void testLogin() {
         User user = User.login("invalid", "password");
         assertNull(user);

         user = User.login("validuser", "password");
         assertEquals("validuser", user.getUsername());
       }

       /**
        * Tests that the custom Tapestry IMonitor will rollback changes
    to the DataContext.
        * An assumption is made that Tapestry will do the right thing and
    fire to our monitor.
        */
       public void testException() {
         CollexMonitorFactory factory = new CollexMonitorFactory();
         IMonitor monitor = factory.createMonitor(null); // WebRequest
    parameter is not used by our monitor factory

         User user = User.login("validuser", "password");
         user.setPassword("something different");

         // this is what happens if a Tapestry listener method throws an
    exception
         monitor.serviceException(new Exception("test"));

         // ensure password has not been changed
         assertEquals("password", user.getPassword());
       }

    }



    This archive was generated by hypermail 2.0.0 : Tue May 03 2005 - 08:53:25 EDT