dozd/mongo-mapper

Can't run mapper app from within IDE

gliviu opened this issue · 4 comments

Error:

Exception` in thread "main" org.bson.codecs.configuration.CodecConfigurationException: Can't find a codec for class mongo.TestEntity.

Seem to be related to missing META-INF/annotations/eu.dozd.mongo.annotation.Entity

The question is how do I convince Eclipse and probably other IDEs to generate that file.

dozd commented

Mongo-mapper works fine in any IDE, it will be probably problem in your project. I need more info to provide any help - eg. entity you are trying to encode / decode, full stack trace etc.

I followed these steps

    public static void main(String[] args) {
        CodecRegistry codecRegistry = CodecRegistries.fromProviders(MongoMapper.getProviders());
        MongoClientOptions settings = MongoClientOptions.builder().codecRegistry(codecRegistry).build();

        String port = "27017";
        MongoClient client = new MongoClient(new ServerAddress("127.0.0.1", Integer.parseInt(port)), settings);
        String dbName = "mapper_test" + UUID.randomUUID();
        MongoDatabase db = client.getDatabase(dbName);
        
        MongoCollection<TestEntity> collection = db.getCollection("test", TestEntity.class);
        collection.drop();

        TestEntity entity = new TestEntity();
        entity.setChecked(true);
        entity.setName("name");
        entity.setI(2);
        entity.setJ(1);

        collection.insertOne(entity);

        TestEntity returned = collection.find().first();
        Assert.assertEquals(entity.isChecked(), returned.isChecked());
        Assert.assertEquals(entity.getName(), returned.getName());
        Assert.assertEquals(entity.getI(), returned.getI());
        Assert.assertEquals(entity.getJ(), returned.getJ());
        
    }
  • clean project from Project->Clean menu
  • run main method from within Eclipse
  • get exception
Exception in thread "main" org.bson.codecs.configuration.CodecConfigurationException: Can't find a codec for class eu.dozd.mongo.entity.TestEntity.
	at org.bson.codecs.configuration.CodecCache.getOrThrow(CodecCache.java:46)
	at org.bson.codecs.configuration.ProvidersCodecRegistry.get(ProvidersCodecRegistry.java:63)
	at org.bson.codecs.configuration.ProvidersCodecRegistry.get(ProvidersCodecRegistry.java:37)
	at com.mongodb.MongoCollectionImpl.getCodec(MongoCollectionImpl.java:591)
	at com.mongodb.MongoCollectionImpl.insertOne(MongoCollectionImpl.java:314)
	at com.mongodb.MongoCollectionImpl.insertOne(MongoCollectionImpl.java:307)
	at eu.dozd.mongo.App.main(App.java:39)

If I 'mvn clean package' and run again, I get no error.
So I checked what is the difference between maven clean build and Eclipse clean build.
It proved that when using maven this file is present:
mongo-mapper\target\test-classes\META-INF\annotations\eu.dozd.mongo.annotation.Entity
Using eclipse clean build does not generate the file. If I add the file manually the error is gone.

I can also confirm this. Running a WAR file on a TOMEE Server and the codec is not found after cleaning the project, but running a clean install from Maven with Fongo works.

Upon @gliviu's observation, I found that target\<My War Folder>\META-INF\ was completely empty, and when adding it caused the codec to work again.

Please fix this, as this is a wonderful dependency while waiting for the new PojoCodec in 3.5. Thanks!

Edit: I think it's a bug with the @IndexAnnotated annotation, and when MapperCodecProvider is trying to retrieve the class. Most likely a bug in ClassIndex (Solely with Eclipse?) They seem to have an Eclipse problem. And a quick solution would be to add eu.dozd.mongo.annotation.Entity to your project's Factory Path (Read here). Just thought that might help.

dozd commented

@poeia Yeah, that's the cause. I'll add info to the README (copy from classindex) about usage in Eclipse. But probably can't do anything other with it. I'm using Intellij IDEA and everything is working fine.

Eclipse uses its own Java compiler which is not strictly standard compliant and requires extra configuration. In Java Compiler -> Annotation Processing -> Factory Path you need to add ClassIndex jar file. See the screenshot.