title: How do I write a database unit test?
body: <p>I'm using MongoDB, Java, JDO and Maven.</p>
  
  <p>I ran a simple main application that stores some junk data and retrieves it from mongodb and it looks ok, but I want to start writing proper unit tests. Mocking out the actual database interactions doesn't seem very helpful to me so technically I want to write functional tests that check the full interaction with a database.</p>
  
  <p>My unit test is set up like this:</p>
  
  <pre><code>static final Logger LOG = LoggerFactory.getLogger(DaoTest.class);
  static final int PORT = 100001;
  static Process mongod;
  static PersistenceManagerFactory pmf;
  
  // Class under test.
  Dao dao;
  
  @BeforeClass
  public static void beforeAll() throws Exception {
    File mongoDir = new File(
        System.getProperty("java.io.tmpdir"),
        "mongodb-" + System.currentTimeMillis());
    mongoDir.deleteOnExit();
    mongod = Runtime.getRuntime().exec(String.format(
        "/bin/sh -c mongod --dbpath=%s --port=%d",
        mongoDir.getAbsolutePath(),
        PORT));
    LOG.info("Mongodb using {} on port {}.", mongoDir.getAbsolutePath(), PORT);
    Thread.sleep(1000);
    pmf = JDOHelper.getPersistenceManagerFactory("mongodbtest");
    LOG.info("DB connection URL: {}.", pmf.getConnectionURL());
  }
  
  @AfterClass
  public static void afterAll() throws Exception {
    mongod.destroy();
  }
  
  @Before
  public void setUp() throws Exception {
    dao = new Dao(pmf);
  }
  </code></pre>
  
  <p>src/test/resources/META-INF/persistence.xml is like this:</p>
  
  <pre><code>&lt;?xml version="1.0" encoding="UTF-8" ?&gt;
  &lt;persistence ...&gt;
    &lt;persistence-unit name="mongodbtest"&gt;
      &lt;properties&gt;
        &lt;property name="javax.jdo.PersistenceManagerFactoryClass"
            value="org.datanucleus.api.jdo.JDOPersistenceManagerFactory" /&gt;
        &lt;property name="javax.jdo.option.ConnectionURL" value="mongodb://localhost:100001/contacts"/&gt;
        &lt;property name="javax.jdo.option.RetainValues" value="true"/&gt;
        &lt;property name="datanucleus.autoCreateSchema" value="true" /&gt;
        &lt;property name="datanucleus.validateTables" value="false" /&gt;
        &lt;property name="datanucleus.validateConstraints" value="false" /&gt;
        &lt;property name="datanucleus.storeManagerType" value="mongodb" /&gt;
      &lt;/properties&gt;
    &lt;/persistence-unit&gt;
  &lt;/persistence&gt;
  </code></pre>
  
  <p>And finally I execute my unit test with mvn clean test and that alone will work until I add an actual test that attempts save data. I get the following error:</p>
  
  <pre><code>Mongodb using /var/folders/00/0l550000h01000cxqpysvccm002cmm/T/mongodb-1373820849219 on port 100001.
  DB connection URL: mongodb://localhost:100001/contacts.
  Jul 14, 2013 12:54:10 PM com.mongodb.DBTCPConnector initDirectConnection
  WARNING: Exception executing isMaster command on localhost/127.0.0.1:27017
  java.io.IOException: couldn't connect to [localhost/127.0.0.1:27017] bc:java.net.ConnectException: Connection refused
      at com.mongodb.DBPort._open(DBPort.java:214)
      at com.mongodb.DBPort.go(DBPort.java:107)
  
  ...
  
  Jul 14, 2013 12:54:10 PM com.mongodb.DBTCPConnector initDirectConnection
  WARNING: Exception executing isMaster command on localhost/127.0.0.1:27017
  java.io.IOException: couldn't connect to [localhost/127.0.0.1:27017] bc:java.net.ConnectException: Connection refused
      at com.mongodb.DBPort._open(DBPort.java:214)
      at com.mongodb.DBPort.go(DBPort.java:107)
  
  ...
  
  ul 14, 2013 12:54:10 PM com.mongodb.DBPortPool gotError
  WARNING: emptying DBPortPool to localhost/127.0.0.1:27017 b/c of error
  java.io.IOException: couldn't connect to [localhost/127.0.0.1:27017] bc:java.net.ConnectException: Connection refused
      at com.mongodb.DBPort._open(DBPort.java:214)
      at com.mongodb.DBPort.go(DBPort.java:107)
  
  ...
  
  Jul 14, 2013 12:54:10 PM org.datanucleus.store.valuegenerator.AbstractGenerator obtainGenerationBlock
  INFO: Error encountered allocating block of IDs : can't call something : localhost/127.0.0.1:27017//localhost:100001/contacts
  </code></pre>
  
  <p>127.0.0.1:27017 is mongodb's default settings but I have no idea why it's using that. I can see it's picking up the configs from my persistence.xml file so I'm confused. The mongo <a href="http://docs.mongodb.org/manual/reference/connection-string/" rel="nofollow">docs</a> say the connection string URL format is:</p>
  
  <pre><code>mongodb://[username:password@]host1[:port1][,host2[:port2],...[,hostN[:portN]]][/[database][?options]]
  </code></pre>
  
  <p>So far I've only been running this through maven because that's only as far as I got so far but another question I'll have eventually is how to run these unit tests in Eclipse. I assume the byte code enhancement process has to happen for these tests to be run in Eclipse and I don't know how to set that up.</p>
  
  <p>I'm guessing I'm not the first person to want to do something like this though. Are there any standard practices for writing functional database tests in Java? Am I going about it all wrong?</p>