MongoDB に Spring-Data を使用しています。
バージョン情報 - org.mongodb.mongo-java-driver バージョン 2.10.1、org.springframework.data.spring-data-mongodb バージョン 1.2.1.RELEASE。
hereで定義されているものに似たケースがあります(フォーマットが申し訳ありません...):
spring-data-mongodb を使用して Java でアプリの開発を開始したところ、解決できない問題に遭遇しました。
次のようなドキュメント Bean がいくつかあります。
@Document(collection="myBeanBar")
public class BarImpl implements Bar {
String id;
Foo foo;
// More fields and methods ...
}
@Document
public class FooImpl implements Foo {
String id;
String someField;
// some more fields and methods ...
}
そして、次のような検索を呼び出すだけのメソッドを持つリポジトリ クラスがあります。
public List<? extends Bar> findByFooField(final String fieldValue) {
Query query = Query.query(Criteria.where("foo.someField").is(fieldValue));
return getMongoOperations().find(query, BarImpl.class);
}
Bar の保存は問題なく機能します。Foo と Bar の両方の「_class」属性とともに mongo に保存されます。ただし、Foo の属性で検索すると、次のような例外がスローされます。
Exception in thread "main" java.lang.IllegalArgumentException: No
property someField found on test.Foo!
at org.springframework.data.mapping.context.AbstractMappingContext.getPersistentPropertyPath(AbstractMappingContext.java:225)
at org.springframework.data.mongodb.core.convert.QueryMapper.getPath(QueryMapper.java:202)
at org.springframework.data.mongodb.core.convert.QueryMapper.getTargetProperty(QueryMapper.java:190)
at org.springframework.data.mongodb.core.convert.QueryMapper.getMappedObject(QueryMapper.java:86)
at org.springframework.data.mongodb.core.MongoTemplate.doFind(MongoTemplate.java:1336)
at org.springframework.data.mongodb.core.MongoTemplate.doFind(MongoTemplate.java:1322)
at org.springframework.data.mongodb.core.MongoTemplate.find(MongoTemplate.java:495)
at org.springframework.data.mongodb.core.MongoTemplate.find(MongoTemplate.java:486)
与えられた解決策は、抽象クラスで @TypeAlias アノテーションを使用することでした。これにより、フレームワークに特定の実装 (この場合はFooImpl ) を使用するように指示されました。
私の場合、抽象メンバーの代わりにインターフェイスメンバーがあります。
@Document(collection="myBeanBar")
public class BarImpl implements Bar {
String id;
IFoo foo;
// More fields and methods ...
}
デフォルトの実装を提供するインターフェイスIFooに注釈を付けることには非常に消極的です。代わりに、@JsonTypeInfoのように、実装するBarImplクラスのコンテキストでこのフィールドのデフォルトの実装をフレームワークに伝えたいと思います。
@Document(collection="myBeanBar")
public class BarImpl implements Bar {
String id;
@JsonTypeInfo(use = Id.CLASS, defaultImpl = FooImpl.class)
IFoo foo;
// More fields and methods ...
}
this answerを見つけました。多かれ少なかれ、インターフェースの使用を避けるように言っています。しかし、より良い選択肢がないかどうかを教えていただければ幸いです。
何か案は?
ありがとう!