I am using Hibernate OGM (5.2.0.Alpha1) with Mongodb (3.4)
@Entity
@Table(name = "service")
@JsonInclude(Include.NON_EMPTY)
public class Service {
@Id
@GeneratedValue(strategy = GenerationType.IDENTITY)
@Column(name = "SERVICE_ID", unique = true, nullable = false)
@JsonSerialize(using = ToStringSerializer.class)
public ObjectId id;
private String name;
@ManyToOne
@JsonIgnore
public Lab lab;
getter....
setter....
}
@Entity
@Table(name = "lab")
@JsonInclude(Include.NON_EMPTY)
// @JsonFilter(value=SalesUtils.MY_CUSTOM_FILTER_FOR_LAB)
public class Lab {
@Id
@GeneratedValue(strategy = GenerationType.IDENTITY)
@JsonSerialize(using = ToStringSerializer.class)
@Column(name = "LAB_ID", unique = true, nullable = false)
public ObjectId id;
private String name;
@OneToMany(mappedBy = "lab")
public List<Service> listOfServices;
getter....
setter....
}
Dao Layer:
public <T> List<T> executeQuery(String query, Integer startPosition, Integer noOfRecords, T t) {
List<T> listOfT = new ArrayList<>();
if (SalesUtils.isObjectisNullOrEmpty(startPosition, noOfRecords)) {
listOfT = entityManager.createNativeQuery(query.toString(), t.getClass()).getResultList();
} else {
listOfT = entityManager.createNativeQuery(query.toString(), t.getClass()).setFirstResult(startPosition)
.setMaxResults(noOfRecords).getResultList();
}
return SalesUtils.isListIsNullOrEmpty(listOfT) ? new ArrayList<>() : listOfT;
}
Service Layer : (Issue : Lab name : null)
@Transaction
public void executeQuery(){
String query = "db.service.find({} , {"name":1})";
List<Service> listOfServices = myDao.executeQuery(query , null , null ,new Service());
String anotherQuery = " { $query : { name : "CDG Service"}}";
List<Service> listOfAnotherServices = myDao.executeQuery(query , null , null ,new Service());
if (!SalesUtils.isListIsNullOrEmpty(listOfAnotherServices )) {
System.out.println(listOfAnotherServices.get(0).getName());
System.out.println(listOfAnotherServices.get(0).getLab().getName()); //null
}
}
Service Layer : (Temporary Solution)
@Transaction
public void executeQuery(){
//Temporary solution : added lab_LAB_ID field in below 1st query
String query = "db.service.find({} , {"name":1,"lab_LAB_ID":1})";
List<Service> listOfServices = myDao.executeQuery(query , null , null ,new Service());
String anotherQuery = " { $query : { name : "CDG Service"}}";
List<Service> listOfAnotherServices = myDao.executeQuery(query , null , null ,new Service());
if (!SalesUtils.isListIsNullOrEmpty(listOfAnotherServices )) {
System.out.println(listOfAnotherServices.get(0).getName());
System.out.println(listOfAnotherServices.get(0).getLab().getName()); //not null
}
}
Detail Explanation :
Here i only get 'name' field of service table using 1st query execution (variable name = query) and then executed 2nd query(variable name = anotherQuery) , but can not get lab object.
so i get 'name' and 'lab_LAB_ID' both fields using 1st query execution (variable name = query) and then i executed 2nd query(variable name = anotherQuery) so not i can successfully get lab object.
I don't understand this. It seems like 2nd query result is dependent on 1st query result fields even if query is different and variable name is also different.
Is I am right?
Using native queries, if you choose to apply a projection on the root class you have to remove toEntity, because partial a entity extraction should not be allowed. It is likely that an exception throwing will be introduced in the next versions of the product to prevent this use. This is the current behaviour of Hibernate ORM (5.2 | 5.3) on H2 dialect too.