我正在使用 DataNucleus 3.0.0-release JDO 实现将我的 Java 应用程序连接到 MongoDB。
我的 CLASSPATH 中的相关 JAR 如下:
- datanucleus-api-jdo-3.0.0-release.jar
- datanucleus-core-3.0.0-release.jar
- datanucleus-jdo-query-3.0.0-release.jar
- datanucleus-mongodb-3.0.0-release.jar
- mongo-java-driver-2.5.2.jar
我坚持的课程如下:
@PersistenceCapable(detachable = "true")
public class Record implements Serializable, Cacheable<String> {
private static final long serialVersionUID = 9022509306966814904L;
@PrimaryKey
@Persistent(defaultFetchGroup = "true", valueStrategy = IdGeneratorStrategy.IDENTITY)
private String id;
@Name
@Persistent(defaultFetchGroup = "true")
private String name;
@Name
@Persistent(defaultFetchGroup = "true")
private String surname;
@Persistent(defaultFetchGroup = "true")
private Date dateOfBirth;
@Persistent(defaultFetchGroup = "true")
private Date dateRecorded;
@Persistent(defaultFetchGroup = "true")
private String locationId;
@Persistent(embedded = "true", defaultFetchGroup = "true")
private CustomLocation customLocation;
@Persistent(defaultFetchGroup = "true")
private Category category;
@Persistent(embedded = "true", defaultFetchGroup = "true")
private CustomCategory customCategory;
@Persistent(defaultFetchGroup = "true")
private String description;
@Persistent(embeddedElement = "true", defaultFetchGroup = "true")
private List<StoredImageInfo> images;
@Persistent(embeddedElement = "true", defaultFetchGroup = "true")
private List<StoredAudioInfo> audio;
@Persistent(embeddedElement = "true", defaultFetchGroup = "true")
private List<StoredFileInfo> files;
@Persistent(defaultFetchGroup = "true")
private ModerationMode moderationMode;
@Persistent(defaultFetchGroup = "true")
private VisibilityMode visibilityMode;
@Persistent(embedded = "true", defaultFetchGroup = "true")
private UserProfileSummary owner;
@Persistent(embeddedElement = "true", defaultFetchGroup = "true")
private Map<String, UserProfileSummary> editors;
@Persistent(embeddedElement = "true", defaultFetchGroup = "true")
private Map<String, UserProfileSummary> connections;
@Persistent(embeddedElement = "true", defaultFetchGroup = "true")
private Map<String, RecordSummary> recordConnections;
@Persistent(defaultFetchGroup = "true")
private RecordType type;
@Persistent(defaultFetchGroup = "true")
private Date expiry;
public Record() {
}
public Record(Record copy) {
deepCopy(copy);
}
...
}
和CustomLocation
班级:
@PersistenceCapable(embeddedOnly="true")
public class CustomLocation implements Serializable {
private static final long serialVersionUID = -7754029273366194129L;
@PrimaryKey
@Persistent(defaultFetchGroup = "true", valueStrategy = IdGeneratorStrategy.IDENTITY)
private String id;
@Persistent(defaultFetchGroup = "true")
private String city;
@Persistent(defaultFetchGroup = "true")
private String countryKey;
@Persistent(defaultFetchGroup = "true")
private String locale;
@SuppressWarnings("unused")
private CustomLocation() {
// for serialization
}
...
}
尝试从数据库中获取对象的代码如下:
PersistenceManager pm = MyPersistenceManagerFactory.get().getPersistenceManager();
Record record = null;
try {
record = pm.getObjectById(Record.class, recordId);
}
catch (JDOObjectNotFoundException onfe) {
// handle
}
catch (Exception e) {
// handle
}
以下是产生的错误:
java.lang.NullPointerException
at org.datanucleus.store.mongodb.fieldmanager.FetchFieldManager.fetchStringField(FetchFieldManager.java:243)
at org.datanucleus.state.AbstractStateManager.replacingStringField(AbstractStateManager.java:2165)
at com.myproject.location.domain.CustomLocation.jdoReplaceField(CustomLocation.java)
at com.myproject.location.domain.CustomLocation.jdoReplaceFields(CustomLocation.java)
at org.datanucleus.state.JDOStateManagerImpl.replaceFields(JDOStateManagerImpl.java:1989)
at org.datanucleus.state.JDOStateManagerImpl.replaceFields(JDOStateManagerImpl.java:2009)
at org.datanucleus.store.mongodb.fieldmanager.FetchFieldManager.fetchObjectField(FetchFieldManager.java:353)
at org.datanucleus.state.AbstractStateManager.replacingObjectField(AbstractStateManager.java:2182)
at com.myproject.domain.Record.jdoReplaceField(Record.java)
at com.myproject.domain.Record.jdoReplaceFields(Record.java)
at org.datanucleus.state.JDOStateManagerImpl.replaceFields(JDOStateManagerImpl.java:1989)
at org.datanucleus.state.JDOStateManagerImpl.replaceFields(JDOStateManagerImpl.java:2009)
at org.datanucleus.store.mongodb.MongoDBPersistenceHandler.fetchObject(MongoDBPersistenceHandler.java:600)
at org.datanucleus.state.JDOStateManagerImpl.loadFieldsFromDatastore(JDOStateManagerImpl.java:1696)
at org.datanucleus.state.JDOStateManagerImpl.validate(JDOStateManagerImpl.java:3576)
at org.datanucleus.ObjectManagerImpl.findObject(ObjectManagerImpl.java:3246)
at org.datanucleus.api.jdo.JDOPersistenceManager.getObjectById(JDOPersistenceManager.java:1731)
at org.datanucleus.api.jdo.JDOPersistenceManager.getObjectById(JDOPersistenceManager.java:1749)
at com.myproject.server.GetRecordHandler.execute(GetRecordHandler.java:37)
谁能发现问题所在?
注意:我知道 DataNucleus 3.1.0-release 可用,但我不能使用它,因为它的增强器有问题。
更新:我对这个问题做了一些进一步的测试,结果发现 DataNucleusNullPointerException
为那些embedded
也被标记为在 中defaultFetchGroup
并且值为null
.