ResultSet error executing #Query in JPA Reposity, using nativeQuery = true - java

I am working on a web application using:
Spring Boot
PostgreSQL
JPA and Hibernate.
I have a table called role and another page. Among them there is a many-to-many table with ID's. What I'm trying to get is the list of pages that correspond to a role, so I'm trying to retrieve the list of pages from the id of the role and executing a query to bring the list. The problem is that I have an error in the ResultSet because it tells me that it does not find a column with the name page_id.
Example:
I have executed the query separately and this brings me results correctly.
select p.url from role_page rp, page p where rp.role_id = 6 and rp.page_id = p.page_id;
Output:
Output of the query
Then I made a call to the function to get the list and check it to make sure I get results.
public void rolesAndPages(){
List<Page> pages = pageRepository.findPagePerRole(6);
for (Page page: pages
) {
System.out.println(page.getUrl());
}
}
And throws the error described above:
org.postgresql.util.PSQLException: The column name page_id was not found in this ResultSet.
My Repository:
#Repository("pageRepository")
public interface PageRepository extends JpaRepository<Page, Long> {
#Query(value = "select p.url from role_page rp, page p where rp.role_id = ?1 and rp.page_id = p.page_id", nativeQuery = true)
List<Page> findPagePerRole(Integer id);
}
Role.java
#Entity
#Table(name = "app_role")
public class Role {
#Id
#SequenceGenerator(name="pk_sequence",sequenceName="messagesounds_id_seq", allocationSize=1)
#GeneratedValue(strategy=GenerationType.SEQUENCE,generator="pk_sequence")
#Column(name="role_id")
private int id;
#Column(name="authority")
#NotEmpty(message = "*Please provide a name")
private String authority;
#ManyToMany(cascade = CascadeType.ALL)
#JoinTable(name = "role_page", joinColumns = #JoinColumn(name = "role_id"), inverseJoinColumns = #JoinColumn(name = "page_id"))
private Set<Page> pages;
public void setPages(Set<Page> pages) {
this.pages = pages;
}
public Set<Page> getPages() {
return pages;
}
public Role() {}
public Role(String authority) {
this.authority = authority;
}
public Role(String authority, Set<Page> pages){
this.authority = authority;
this.pages = pages;
}
public int getId() {
return id;
}
public void setId(int id) {
this.id = id;
}
public String getAuthority() {
return authority;
}
public void setAuthority(String authority) {
this.authority = authority;
}
}
Page.java
#Entity
#Table(name = "page")
public class Page {
#Id
#SequenceGenerator(name = "pk_sequence", sequenceName = "messagesounds_id_seq", allocationSize = 1)
#GeneratedValue(strategy = GenerationType.SEQUENCE, generator = "pk_sequence")
#Column(name = "page_id")
private int id;
#Column(name = "name_page")
#NotEmpty(message = "*Please provide a name")
private String name;
#Column(name = "url")
#NotEmpty(message = "*Please provide an url")
private String url;
#Column(name = "description")
#NotEmpty(message = "*Please provide a description")
private String description;
#ManyToMany(mappedBy = "pages")
private Set<Role> roles;
public Page() {
}
public Page(String name_page) {
this.name = name_page;
}
public Page(String name_page, Set<Role> roles) {
this.name = name_page;
this.roles = roles;
}
public int getId() {
return id;
}
public void setId(int id) {
this.id = id;
}
public String getName() {
return name;
}
public void setName(String name) {
this.name = name;
}
public String getUrl() {
return url;
}
public void setUrl(String url) {
this.url = url;
}
public String getDescription() {
return description;
}
public void setDescription(String description) {
this.description = description;
}
public Set<Role> getRoles() {
return roles;
}
public void setRoles(Set<Role> roles) {
this.roles = roles;
}
}

The error is quite explicite, you need to select page_id column to make it work, not only p.url.
Try this to retrieve every column of Page :
#Query(value = "select p.* from role_page rp, page p where rp.role_id = ?1 and rp.page_id = p.page_id", nativeQuery = true)
Or, this to retrieve every columns of tables Page and Role_Page :
#Query(value = "from role_page rp, page p where rp.role_id = ?1 and rp.page_id = p.page_id", nativeQuery = true)
The both queries should work.

Did you tried :
#Query(value = "select p.url from role_page rp, page p where rp.id = ?1 and rp.id = p.id")

Related

Hibernate - Mapping a ManyToMany Join Table With Unique Key

I have tables User, Roles, Groups and a join table GroupRoles. A user can have many Roles (some of which are not group specific), and a Group can have many roles. Since Roles can be group related I need to associate a groupID with them and hence GroupRoles has a unique key of userID, groupID and roleID. I need userID as part of the key as I need to know what Roles are associated to a user. In hibernate is mapping a unique key like this the same as mapping a composite key, where I would have something along the lines of
#Embeddable
public class GroupRoleKey implements Serializable {
#Column(name="userID")
private Long userID;
#Column(name="groupID")
private Long groupID;
#Column(name="roleID")
private Long roleID;
protected GroupRoleKey(){}
public GroupRoleKey(Long userID, Long roleID, Long groupID) {
this.userID = userID;
this.roleID = roleID;
this.groupID = groupID
}
Honestly I'm not sure if this is even the best way to represent the User - Role - Group relation, any advice would be appreciated. I need to display a Users Roles within each group they belong to, for example I may want to display Bob's Roles Admin and Teacher for Group 1 and role Group Admin for group 2. I need to know which roles correspond to what group and what roles correspond to what user.
EDIT:
Group Entity:
#Table(name="FocusGroups")
#Entity
#JsonIdentityInfo(generator = ObjectIdGenerators.PropertyGenerator.class,
property = "groupID")
public class Group {
#Id
#GeneratedValue(strategy = GenerationType.IDENTITY)
private Long groupID;
private String groupName;
#ManyToMany
#JoinTable(name = "GroupMembers",
joinColumns = #JoinColumn(
name = "groupID"),
inverseJoinColumns = #JoinColumn(
name = "userID"))
private Set<User> groupMembers = new HashSet<>();
#ManyToMany
#JoinTable(name = "GroupRoles",
joinColumns =
#JoinColumn(
name = "groupID"),
inverseJoinColumns = #JoinColumn(
name = "roleID"))
private Set<Role> roles = new HashSet<>();
#ManyToOne(fetch = FetchType.EAGER, optional = true)
#JoinColumn(name="frameworkID", nullable = true)
private Framework framework;
public Group(){}
public Group(String groupName, Set<User> groupMembers, Framework framework) {
this.groupName = groupName;
this.groupMembers = groupMembers;
this.framework = framework;
}
public Long getGroupID() {
return groupID;
}
public void setGroupID(Long groupID) {
this.groupID = groupID;
}
public String getGroupName() {
return groupName;
}
public void setGroupName(String groupName) {
this.groupName = groupName;
}
public Set<User> getGroupMembers() {
return groupMembers;
}
public void setGroupMembers(Set<User> groupMembers) {
this.groupMembers = groupMembers;
}
public void addMembers(Set<User> groupMembers){
this.groupMembers.addAll(groupMembers);
}
public void addMember(User groupMember){
this.groupMembers.add(groupMember);
}
public String groupMembersToString(){
String out = "";
int count = 0;
if(groupMembers.size() > 0){
for(User user: groupMembers){
if(count >= 1){
out += ", ";
}
out += user.getUsername();
count++;
}
}else{
out = "No members";
}
return out;
}
public boolean hasMember(String groupMemberName) {
for (User member : this.groupMembers) {
if (member.getUsername().equals(groupMemberName)) {
return true;
}
}
return false;
}
public User getGroupMember(String groupMemberName){
for(User member: this.groupMembers){
if(member.getUsername().equals(groupMemberName)){
return member;
}
}
return null;
}
public Framework getFramework() {
return framework;
}
public void setFramework(Framework framework) {
this.framework = framework;
}
public Set<Role> getRoles() {
return roles;
}
public void setRoles(Set<Role> roles) {
this.roles = roles;
}
}
Role:
#Entity
#Table(name = "Roles")
public class Role {
#Id
#GeneratedValue(strategy = GenerationType.IDENTITY)
private Long roleID;
private String roleName;
#ManyToMany
#JoinTable(name = "GroupRoles",
joinColumns =
#JoinColumn(
name = "roleID"),
inverseJoinColumns = #JoinColumn(
name = "groupID", nullable = true))
private Set<Group> groups = new HashSet<>();
protected Role(){}
public Role(String roleName){
this.roleName = roleName;
}
public Long getId() {
return roleID;
}
public void setId(Long id) {
this.roleID = id;
}
public String getName() {
return roleName;
}
public void setName(String roleName) {
this.roleName = roleName;
}
}
User:
#Table(name="Users")
#Entity
#NamedStoredProcedureQueries({
#NamedStoredProcedureQuery(
name = "userRating",
procedureName = "CalculateUserRating",
parameters = {
#StoredProcedureParameter(
name = "userID",
type = Long.class,
mode = ParameterMode.IN),
#StoredProcedureParameter(
name = "focusID",
type = Long.class,
mode = ParameterMode.IN),
#StoredProcedureParameter(
name = "userRating",
type = BigDecimal.class,
mode = ParameterMode.OUT)
})
})
//store a base rating?
public class User {
#Id
#GeneratedValue(strategy=GenerationType.IDENTITY)
private Long userID;
#Column(name = "userHashedPassword")
private String password;
#Column(name = "userName")
private String userName;
#Column(name = "userEmail")
private String email;
#ManyToMany
#JoinTable(name = "GroupMembers",
joinColumns = #JoinColumn(
name = "userID"),
inverseJoinColumns = #JoinColumn(
name = "groupID"))
private Set<Group> usersGroups = new HashSet<>();
#ManyToMany
#JoinTable(name = "UserRoles",
joinColumns = #JoinColumn(
name = "userID"),
inverseJoinColumns = #JoinColumn(
name = "roleID"))
private Set<Role> roles = new HashSet<>();
#OneToMany(mappedBy = "user")
private Set<Rating> ratings;
protected User(){}
public User(String userHashedPassword, String userName, String email, Set<Role> roles){
this.password = userHashedPassword;
this.userName = userName;
this.email = email;
this.roles = roles;
}
public User(String userName, String userHashedPassword){
this.userName = userName;
this.password = userHashedPassword;
}
public Long getUserId() {
return userID;
}
public void setId(Long userID) {
this.userID = userID;
}
public String getPassword(){
return password;
}
public void setPassword(String password){
this.password = password;
}
public String getUsername() {
return userName;
}
public void setUsername(String name) {
this.userName = name;
}
public String getEmail() {
return email;
}
public void setEmail(String email) {
this.email = email;
}
public Set<Role> getRoles() {
return roles;
}
public void setRoles(Set<Role> roles) {
this.roles = roles;
}
public Set<Rating> getRatings() {
return ratings;
}
public void setRatings(Set<Rating> ratings) {
this.ratings = ratings;
}
public String rolesToString(){
String outputRoles = "";
int count = 0;
for(Role role: roles){
if(count >= 1){
outputRoles += ", ";
}
outputRoles += role.getName();
count++;
}
return outputRoles;
}
public void removeRole(Role role){
this.roles.remove(role);
}
public Set<Group> getGroups() {
return usersGroups;
}
public void addGroup(Group group) {
this.usersGroups.add(group);
}
public void addGroups(Set<Group> groups) {
this.usersGroups.addAll(groups);
}
public Set<Group> getUsersGroups() {
return usersGroups;
}
public void setUsersGroups(Set<Group> usersGroups) {
this.usersGroups = usersGroups;
}
public String groupsToString(){
String outputGroups = "";
int count = 0;
if(usersGroups.size() > 0){
for(Group group: usersGroups){
if(count >= 1){
outputGroups += ", ";
}
outputGroups += group.getGroupName();
count++;
}
}else{
outputGroups = "None";
}
return outputGroups;
}
}

SQL Query with Entity Manager

I've been thinking about how to create a proper query for my purpose but I'm not sure how should I approach it. It's a Spring web app, the website is similar to Twitter.
What I'm trying is to get the messages from who the user that requested the function follows. Saying shortly, a Twitter timeline, there are the classes:
User class
//Imports
#Entity
#Table (name = "USUARIOS")
public class UsuarioVO implements Serializable {
//Not important class attributes and their getters/setters
#Id
#GeneratedValue(strategy = GenerationType.IDENTITY)
public Long getId() {
return id;
}
#ManyToMany(cascade = CascadeType.ALL)
#JoinTable(name = "USER_FOLLOW",
joinColumns = #JoinColumn(name = "FOLLOWED_ID"),
inverseJoinColumns = #JoinColumn(name = "FOLLOWER_ID"))
public Set<UsuarioVO> getFollowers() {
return followers;
}
public void setFollowers(Set<UsuarioVO> followers) {
this.followers = followers;
}
public void addFollower(UsuarioVO user) {
followers.add(user);
user.following.add(this);
}
#ManyToMany(mappedBy = "followers")
public Set<UsuarioVO> getFollowing() {
return following;
}
public void setFollowing(Set<UsuarioVO> following) {
this.following = following;
}
public void addFollowing(UsuarioVO user) {
user.addFollower(this);
}
}
Message class
#Entity
#Table(name = "MENSAJES")
public class MensajeVO implements Serializable{
/**
*
*/
private static final long serialVersionUID = 2819136255644301650L;
private Long id;
private UsuarioVO sender;
private String body;
private Date fecha;
private HashtagVO hashtag;
public MensajeVO() {}
#Id
#GeneratedValue(strategy = GenerationType.IDENTITY)
public Long getId() {
return id;
}
public void setId(Long id) {
this.id = id;
}
#ManyToOne(fetch=FetchType.EAGER)
#JoinColumn(name = "ID_SENDER")
public UsuarioVO getSender() {
return sender;
}
public void setSender(UsuarioVO sender) {
this.sender = sender;
}
#Column(name = "BODY")
public String getBody() {
return body;
}
public void setBody(String body) {
this.body = body;
}
#Temporal(TemporalType.TIMESTAMP)
#Column(name = "FECHA_ENVIO")
public Date getFecha() {
return fecha;
}
public void setFecha(Date fecha) {
this.fecha = fecha;
}
#ManyToOne(fetch = FetchType.EAGER)
#JoinColumn(name = "ID_HASHTAG")
public HashtagVO getHashtag() {
return hashtag;
}
public void setHashtag(HashtagVO hashtag) {
this.hashtag = hashtag;
}
}
The first approach I thought was getting the Set of following from the user and query each one of them to retrieve the messages, but there is a problem with that, I want to order the query by date, with that approach it would only order by date the message of each user, like:
User1 messages ordered by Date
User2 messages ordered by Date
etc..
I was thinking about doing this with an Inner Join, but I'm not sure how should I build the query. An example of a working query:
public Set<MensajeVO> findByUser(Long userid) {
Query query = this.entityManager.createQuery(
"SELECT m FROM MensajeVO m WHERE m.sender.id = ?1 ORDER BY m.fecha DESC", MensajeVO.class);
query.setParameter(1, userid);
return new HashSet<MensajeVO>(query.getResultList());
}
Thanks in advance.
EDIT
In SQL this is the query
SELECT * FROM mensajes INNER JOIN user_follow ON mensajes.ID_SENDER = user_follow.FOLLOWED_ID WHERE user_follow.FOLLOWER_ID = ?
But I don't know how to get user_follow in Java, since is a ManyToMany field.
Figured it out, posting it in case it helps anyone:
Query query = this.entityManager.createQuery(
"SELECT m FROM MensajeVO m WHERE EXISTS(SELECT 1 FROM UsuarioVO u JOIN u.followers fr WHERE fr.id = ?1) OR m.sender.id = ?2 ORDER BY m.fecha DESC", MensajeVO.class);
query.setParameter(1, userid);
query.setParameter(2, userid);
Search for the messages sent by people followed by the user or messages sent by the user.

Hibernate HQL Join Query DOT node with no left-hand-side

I have two model classes
Application.java
#Entity
#Table(name = "Application", catalog = "mysqldb")
#XmlRootElement
public class Application extends BaseObject implements Serializable {
private Long appId;
private Long userId;
private String name;
private String desc;
#Id
#Column(name = "AppId")
#GeneratedValue(strategy = GenerationType.AUTO)
public Long getAppId() {
return this.appId;
}
public void setAppId(Long appId) {
this.appId = appId;
}
#Column(name = "userId", nullable = false)
public Long getUserId() {
return this.userId;
}
public void setUserId(Long userId) {
this.userId = userId;
}
#Column(name = "name", length = 128, nullable = false)
public String getName() {
return this.name;
}
public void setName(String name) {
this.name = name;
}
#Column(name = "Desc")
public String getDesc() {
return this.desc;
}
public void setDesc(String desc) {
this.desc = desc;
}
}
User.java
#Entity
#Table(name="User",catalog="mysqldb")
#XmlRootElement
public class Client extends BaseObject implements Serializable {
private Long userId;
private String name;
#Id
#Column(name="userId")
#GeneratedValue(strategy=GenerationType.AUTO)
public Long getUserId() {
return this.userId;
}
public void setClientId(Long clientId) {
this.clientId = clientId;
}
#Column(name="Name", length=128)
public String getName() {
return this.name;
}
public void setName(String name) {
this.name = name;
}
}
I have not mentioned any relationship between both.
I am trying to get a list of applications with user ID and also to get the name of user.
In my ApplicationDaoImpl java class I have the following method.
#Override
public List<ApplicationObj> getAllByUser(
Long userId) {
String queryString = "select application.appId as appId, application.userId as userId, user.name as name, application.name as name"
+ " from com.mydb.model.Application application join com.mydb.model.User user"
+ " with application.userId = user.userId"
+ " where application.userId=?";
Session session = getSession();
Query query = session.createQuery(queryString);
query.setParameter(0, userId);
List list = query.list();
return new ArrayList<ApplicationObj>();
}
I am trying to get the result and set in a new object. (Setting to new object is not done yet.)
When I try executing this, I get the following exception
java.lang.IllegalStateException: DOT node with no left-hand-side!
at org.hibernate.hql.internal.ast.tree.DotNode.getLhs(DotNode.java:616)
at org.hibernate.hql.internal.ast.tree.DotNode.getDataType(DotNode.java:595)
at org.hibernate.hql.internal.ast.HqlSqlWalker.createFromJoinElement(HqlSqlWalker.java:380)
at org.hibernate.hql.internal.antlr.HqlSqlBaseWalker.joinElement(HqlSqlBaseWalker.java:3516)
at org.hibernate.hql.internal.antlr.HqlSqlBaseWalker.fromElement(HqlSqlBaseWalker.java:3302)
at org.hibernate.hql.internal.antlr.HqlSqlBaseWalker.fromElementList(HqlSqlBaseWalker.java:3180)
at org.hibernate.hql.internal.antlr.HqlSqlBaseWalker.fromClause(HqlSqlBaseWalker.java:706)
at org.hibernate.hql.internal.antlr.HqlSqlBaseWalker.query(HqlSqlBaseWalker.java:562)
at org.hibernate.hql.internal.antlr.HqlSqlBaseWalker.selectStatement(HqlSqlBaseWalker.java:299)
at org.hibernate.hql.internal.antlr.HqlSqlBaseWalker.statement(HqlSqlBaseWalker.java:247)
at org.hibernate.hql.internal.ast.QueryTranslatorImpl.analyze(QueryTranslatorImpl.java:248)
at org.hibernate.hql.internal.ast.QueryTranslatorImpl.doCompile(QueryTranslatorImpl.java:183)
at org.hibernate.hql.internal.ast.QueryTranslatorImpl.compile(QueryTranslatorImpl.java:136)
at org.hibernate.engine.query.spi.HQLQueryPlan.<init>(HQLQueryPlan.java:105)
at org.hibernate.engine.query.spi.HQLQueryPlan.<init>(HQLQueryPlan.java:80)
at org.hibernate.engine.query.spi.QueryPlanCache.getHQLQueryPlan(QueryPlanCache.java:168)
at org.hibernate.internal.AbstractSessionImpl.getHQLQueryPlan(AbstractSessionImpl.java:221)
at org.hibernate.internal.AbstractSessionImpl.createQuery(AbstractSessionImpl.java:199)
at org.hibernate.internal.SessionImpl.createQuery(SessionImpl.java:1735)
at com.mypgm.dao.hibernate.ApplicationDaoImpl.getAllByUser(ApplicationDaoImpl.java:74)
How to solve this? Or how to do join query without mapping any relationships

JPA - Get collection from ManyToOne relationship

I have a table Post and Post_Image
#Entity
#Table(name = "post")
#XmlRootElement
#NamedQueries({
#NamedQuery(name = "Post.findAll", query = "SELECT p FROM Post p"),
#NamedQuery(name = "Post.findByPostId", query = "SELECT p FROM Post p WHERE p.postId = :postId"),
#NamedQuery(name = "Post.findByTitle", query = "SELECT p FROM Post p WHERE p.title = :title"),
#NamedQuery(name = "Post.findByCreatedDatetime", query = "SELECT p FROM Post p WHERE p.createdDatetime = :createdDatetime")})
public class Post implements Serializable {
private static final long serialVersionUID = 1L;
#Id
#GeneratedValue(strategy = GenerationType.IDENTITY)
#Basic(optional = false)
#NotNull
#Column(name = "post_id")
private Integer postId;
#Basic(optional = false)
#NotNull
#Size(min = 1, max = 500)
#Column(name = "title")
private String title;
#Basic(optional = false)
#NotNull
#Lob
#Size(min = 1, max = 65535)
#Column(name = "content")
private String content;
#Column(name = "created_datetime")
#Temporal(TemporalType.TIMESTAMP)
private Date createdDatetime;
#JoinColumn(name = "user_id", referencedColumnName = "user_id")
#ManyToOne(optional = false)
private User userId;
#JoinColumn(name = "post_type_id", referencedColumnName = "post_type_id")
#ManyToOne(optional = false)
private PostType postTypeId;
public Post() {
Date date = new Date();
this.createdDatetime =new Date(date.getTime());
}
public Post(Integer postId) {
this.postId = postId;
}
public Post(Integer postId, String title, String content) {
this.postId = postId;
this.title = title;
this.content = content;
}
public Integer getPostId() {
return postId;
}
public void setPostId(Integer postId) {
this.postId = postId;
}
public String getTitle() {
return title;
}
public void setTitle(String title) {
this.title = title;
}
public String getContent() {
return content;
}
public void setContent(String content) {
this.content = content;
}
public Date getCreatedDatetime() {
return createdDatetime;
}
public void setCreatedDatetime(Date createdDatetime) {
this.createdDatetime = createdDatetime;
}
public User getUserId() {
return userId;
}
public void setUserId(User userId) {
this.userId = userId;
}
public PostType getPostTypeId() {
return postTypeId;
}
public void setPostTypeId(PostType postTypeId) {
this.postTypeId = postTypeId;
}
#Override
public int hashCode() {
int hash = 0;
hash += (postId != null ? postId.hashCode() : 0);
return hash;
}
#Override
public boolean equals(Object object) {
// TODO: Warning - this method won't work in the case the id fields are not set
if (!(object instanceof Post)) {
return false;
}
Post other = (Post) object;
if ((this.postId == null && other.postId != null) || (this.postId != null && !this.postId.equals(other.postId))) {
return false;
}
return true;
}
#Override
public String toString() {
return "entity.Post[ postId=" + postId + " ]";
}
}
and
#Entity
#Table(name = "post_image")
#XmlRootElement
#NamedQueries({
#NamedQuery(name = "PostImage.findAll", query = "SELECT p FROM PostImage p"),
#NamedQuery(name = "PostImage.findByPostImageId", query = "SELECT p FROM PostImage p WHERE p.postImageId = :postImageId"),
#NamedQuery(name = "PostImage.findByPath", query = "SELECT p FROM PostImage p WHERE p.path = :path"),
#NamedQuery(name = "PostImage.findByTitle", query = "SELECT p FROM PostImage p WHERE p.title = :title")})
public class PostImage implements Serializable {
private static final long serialVersionUID = 1L;
#Id
#Basic(optional = false)
#NotNull
#Column(name = "post_image_id")
private Integer postImageId;
#Basic(optional = false)
#NotNull
#Size(min = 1, max = 500)
#Column(name = "path")
private String path;
#Basic(optional = false)
#NotNull
#Size(min = 1, max = 500)
#Column(name = "title")
private String title;
#JoinColumn(name = "post_id", referencedColumnName = "post_id")
#ManyToOne(optional = false)
private Post postId;
public PostImage() {
}
public PostImage(Integer postImageId) {
this.postImageId = postImageId;
}
public PostImage(Integer postImageId, String path, String title) {
this.postImageId = postImageId;
this.path = path;
this.title = title;
}
public Integer getPostImageId() {
return postImageId;
}
public void setPostImageId(Integer postImageId) {
this.postImageId = postImageId;
}
public String getPath() {
return path;
}
public void setPath(String path) {
this.path = path;
}
public String getTitle() {
return title;
}
public void setTitle(String title) {
this.title = title;
}
public Post getPostId() {
return postId;
}
public void setPostId(Post postId) {
this.postId = postId;
}
#Override
public int hashCode() {
int hash = 0;
hash += (postImageId != null ? postImageId.hashCode() : 0);
return hash;
}
#Override
public boolean equals(Object object) {
// TODO: Warning - this method won't work in the case the id fields are not set
if (!(object instanceof PostImage)) {
return false;
}
PostImage other = (PostImage) object;
if ((this.postImageId == null && other.postImageId != null) || (this.postImageId != null && !this.postImageId.equals(other.postImageId))) {
return false;
}
return true;
}
#Override
public String toString() {
return "entity.PostImage[ postImageId=" + postImageId + " ]";
}
}
i want to get collection of images for particular post like
Collection objPostImage = objPost.getPostImageCollection()
but manytoone relationship do not provide this functionality to me how can i convert it to one to many or how can i get Image Collection for a post.?
I am new to java so any help and suggestion will be appreciated
thanx in advance...
You can add a java.util.Set of PostImages in your Post object, and use the Hibernate mapping to provide the relationship. This site has a great example of setting up One to Many relationships.
So, for example, you would want to add something like the following to your Post class:
private Set<PostImage> postImages = new HashSet<PostImage>();
#OneToMany(fetch = FetchType.LAZY, mappedBy = "post")
public Set<PostImage> getPostImages() {
return this.postImages;
}
public void setPostImages(Set<PostImage> postImages) {
this.postImages= postImages;
}
Then, in your PostImage class, add a reference to a Post object:
private Post post;
#ManyToOne(fetch = FetchType.LAZY)
#JoinColumn(name = "POST_ID", nullable = false)
public Stock getPost() {
return this.post;
}
public void setPost(Post post) {
this.post= post;
}
After adding that, you will be able to call the getPostImages() method on your Post object.
Try this:
#Entity
#Table(name = "post")
public class Post
{
//....
#OneToMany(mappedBy = "post")
private Set<PostImage> images;
//....
}
#Entity
#Table(name = "post_image")
public class PostImage
{
//....
#JoinColumn(name = "post_id", referencedColumnName = "id")
#ManyToOne(optional = false)
private Post post;
//....
}
The reason why Seth's answer didn't work is because EclipseLink uses fields to access persistence data. (Hibernate uses properties IIRC.) You can specify per class how a JPA provider should access this data.
Using fields:
#Entity
#Access(AccessType.FIELD)
public class SomeEntity
{
#Id
private Long id;
//....
}
Using properties:
#Entity
#Access(AccessType.PROPERTY)
public class SomeEntity
{
private Long id;
//....
#Id
public Long getId()
{
return id;
}
}
However when using #Access(AccessType.PROPERTY) fields are also used (at least in EclipseLink) so something like this is possible:
#Entity
#Access(AccessType.PROPERTY)
public class SomeEntity
{
private Long id;
#Column(name = "text")
private String someText;
//....
#Id
public Long getId()
{
return id;
}
}

trying to run a named query

I’m doing the following:
#Entity
#SqlResultSetMapping(name="getxxxx",
entities=#EntityResult(xxxx.class,
fields = {
#FieldResult(name="x1", column = "x1"),
#FieldResult(name="x2", column = "x2")}))
#NamedNativeQuery(name=" getxxxx ",
query="select x1, x2 from yyyy",
resultSetMapping=" getxxxx ")
} )public class xxxx{
.
.
.
public xxxx() {
}
i get an error:
"Table "xxxx" cannot be resolved", the class xxxx is not a table mapped into my source,
I’m trying to query the DB and return the results into my class
is it possible?
In this situation the first thing I would try would be to remove the #Entity annotation. And then change either the class name or the native query name so that one of them is "xxxx" and one of them is "zzzz," so that I was sure I knew which thing the runtime was complaining about.
It sounds like xxxx should not be an entity bean, since JPA is not happy with returning results in non-entity beans. You must instead call createNativeQuery with just the SQL String. Then call query.getResultList() to fetch the result as a List(Object[]) and use this to fill your non entity result bean.
A few years back I wrote a blog post, that might help you perform advanced native queries with JPA.
Yes, this is possible, but a little tricky. Here's a complex example that should cover most of the bases. In this example:
You have an INVOICE object with a due date;
Each INVOICE has a many-to-one relationship with a COMPANY;
Each INVOICE also has a zero- or one-to-many relationship with a set of ITEMS
Here is the schema:
CREATE TABLE "public"."invoice" (
id SERIAL,
company_id int,
due_date date,
PRIMARY KEY(id)
);
CREATE TABLE "public"."item" (
id SERIAL,
invoice_id int,
description text,
PRIMARY KEY(id)
);
CREATE TABLE "public"."company" (
id SERIAL,
name text,
PRIMARY KEY(id)
);
The INVOICE object (incredibly convoluted example for the sake of completeness):
#Entity
#Table(name = "invoice")
#Loader(namedQuery = "loadInvoiceObject")
#NamedNativeQuery(name="loadInvoiceObject",
query="SELECT " +
"inv.id," +
"inv.due_date," +
"co.*," +
"it.*," +
"FROM invoice inv " +
"JOIN company co ON co.id = inv.company_id " +
"LEFT OUTER JOIN item it ON it.invoice_id = inv.id " +
"WHERE inv.id = :id",
resultSetMapping = "invoicemap")
#SqlResultSetMapping(name = "invoicemap",
entities = {
#EntityResult(entityClass = Invoice.class),
#EntityResult(entityClass = Company.class),
#EntityResult(entityClass = Item.class)
}
)
public class Invoice {
private Integer id;
private Date dueDate;
private Company company;
private List<Item> items = new ArrayList<Item>();
public Invoice() { /* no-args constructor */ }
#Id
#Column(name = "id", nullable = false)
public Integer getId() { return id; }
public void setId(Integer id) { this.id = id; }
#Column(name = "due_date")
#Temporal(TemporalType.DATE)
public Date getDueDate() { return dueDate; }
public void setDueDate(Date dueDate) { this.dueDate = dueDate; }
#ManyToOne(optional = false)
#JoinColumn(name = "company_id", nullable = false)
public Company getCompany() { return company; }
public void setCompany(Company company) { this.company = company; }
#OneToMany(mappedBy = "invoice")
public List<Item> getItems() { return items; }
public void setItems(List<Item> items) { this.items = items; }
}
The ITEM object:
#Entity
#Table(name = "item")
public class Item {
private Integer id;
private String description;
private Invoice invoice;
public Item() { /* no-args constructor */ }
#Id
#Column(name = "id", nullable = false)
public Integer getId() { return id; }
public void setId(Integer id) { this.id = id; }
#Column(name = "description")
public String getDescription() { return description; }
public void setDescription(String description) { this.description = description; }
#ManyToOne(optional = false)
#JoinColumn(name = "invoice_id", nullable = false)
public Invoice getInvoice() { return invoice; }
public void setInvoice(Invoice invoice) { this.invoice = invoice; }
}
The COMPANY object:
#Entity
#Table(name = "company")
public class Company {
private Integer id;
private String name;
private List<Invoice> invoices = new ArrayList<Invoice>();
public Company() { /* no-args constructor */ }
#Id
#Column(name = "id", nullable = false)
public Integer getId() { return id; }
public void setId(Integer id) { this.id = id; }
#Column(name = "name")
public String getName() { return name; }
public void setName(String name) { this.name = name; }
#OneToMany(mappedBy = "company")
public List<Invoice> getInvoices() { return invoices; }
public void setInvoices(List<Invoice> invoices) { this.invoices = invoices; }
}

Categories

Resources