Cannot load fixture/duplicate id with tutorial

635 views
Skip to first unread message

Courtland

unread,
May 3, 2011, 4:57:13 PM5/3/11
to play-fr...@googlegroups.com
Hi -

I'm new to play and am running through the tutorial. I'm currently setup with an in-memory H2 database. I've setup the Bootstrap.java file as indicated in the tutorial

@OnApplicationStart
public class Bootstrap extends Job {
    @Override
    public void doJob() {
        if(User.count() == 0) {
            Fixtures.loadModels("initial-data.yml");
        }
    }
}

However, whenever this is re-run (if I change the application config or the bootstrap.java file), I get an error about duplicate id (bob). If I print the user count to the console, it's zero. Here's the call stack from the console:

play.exceptions.JavaExecutionException: Cannot load fixture initial-data.yml: Cannot load fixture initial-data.yml, duplicate id 'bob' for type models.User
        at play.jobs.Job.call(Job.java:166)
        at Invocation.Job(Play!)
Caused by: java.lang.RuntimeException: Cannot load fixture initial-data.yml: Cannot load fixture initial-data.yml, duplicate id 'bob' for type models.User
        at play.test.Fixtures.loadModels(Fixtures.java:221)
        at Bootstrap.doJob(Bootstrap.java:22)
        at play.jobs.Job.doJobWithResult(Job.java:55)
        at play.jobs.Job.call(Job.java:157)
        ... 1 more
Caused by: java.lang.RuntimeException: Cannot load fixture initial-data.yml, duplicate id 'bob' for type models.User
        at play.test.Fixtures.loadModels(Fixtures.java:186)
        ... 4 more

I'm using the initial-data.yml file directly from the tutorial. If I change the identifier of the first user in initial-data.yml to bob2, I get a different error:

Cannot load fixture initial-data.yml: org.hibernate.PropertyAccessException: could not get a field value by reflection getter of models.User.email. 

I'm not sure what I'm doing wrong here. Any help is appreciated.

Thanks
-Courtland

Andrey Volkov

unread,
Jun 8, 2011, 5:41:34 AM6/8/11
to play-fr...@googlegroups.com
I have found the reason: Play caches ids of loaded entities in Fixtures.idCache. So on the first time after startup it works fine because the cache is empty. However, when Play recreates databases and try to load data the second time, the cache already contains the given ids and Play throws the exception. It happens on the following piece of code (Fixtures.loadModels(String name), lines 185-187):

if (idCache.containsKey(type + "-" + id)) {
   throw new RuntimeException("Cannot load fixture " + name + ", duplicate id '" + id + "' for type " + type);
}

To clear cache it is necessary to call Fixtures.delete() or Fixtures.deleteDatabase(). These methods clear idCache variable.

To resolve your problem just add call of Fixtures.delete() just before you call Fixtures.loadModels("initial-data.yml")
Reply all
Reply to author
Forward
0 new messages