我是Java EE的新手。 我的问题是保留包含我从数据库中提取的数据的数据。它总是说数据被检测到(我知道从数据库中提取数据是有问题的,但我怎么能这样做呢?)。
这就是我所拥有的:
我有三个实体:游戏,流派和发布者
游戏:
@Getter
@Setter
@Entity
public class Game extends BaseEntity {
@ManyToMany(cascade = CascadeType.ALL, fetch = FetchType.EAGER)
@JoinTable(name = "game_genre", joinColumns = { @JoinColumn(name = "game_id") }, inverseJoinColumns = { @JoinColumn(name = "genre_id") })
private Set<Genre> genres = new HashSet<Genre>();
@ManyToOne(cascade = CascadeType.ALL)
@JoinColumn(name="publisher_id")
private Publisher publisher;
@NotNull(message = "Bitte Namen hinzufügen")
private String name;
@Override
public String toString() {
return this.name + this.genres.toString() + this.publisher.toString();
}
}
类型:
@Getter
@Setter
@Entity
public class Genre extends BaseEntity {
private String name;
@ManyToMany(mappedBy = "genres", fetch=FetchType.EAGER)
private Set<Game> games = new HashSet<Game>();
@Override
public String toString() {
return name.toString();
}
}
出版商:
@Getter
@Setter
@Entity
public class Publisher extends BaseEntity {
private String name;
@OneToMany(mappedBy="publisher", fetch = FetchType.EAGER, cascade = CascadeType.ALL )
private Set<Game> games = new HashSet<Game>();
@Override
public String toString() {
return name.toString();
}
}
在我的AbstractDao
中@Override
public void create(final T t) {
this.em.persist(t);
}
@Override
public void update(final T t) {
this.em.merge(t);
}
和每个实体Dao的findAll()方法
@Override
public List<Game> findAll() {
final TypedQuery<Game> query = getEm().createQuery(
"Select a FROM " + Game.class.getSimpleName() + " a", Game.class);
return query.getResultList();
}
我的经理:
manager is an instance of GameManagerBo:
@Stateless
@ManagedBean(name = "manager")
public class GameManagerBo implements GameManager {
@Inject
private Dao<Game> gameDao;
@Inject
private Dao<Genre> genreDao;
@Inject
private Dao<Publisher> publisherDao;
@Override //Same for Genre and Publisher
public void saveGame(Game game) {
if (game.getId() == null) {
this.gameDao.create(game);
} else {
this.gameDao.update(game);
}
}
@Override //Same for Genre and Publisher
public List<Game> readGames() {
return this.gameDao.findAll();
}
@Override
public Publisher getPublisherByName(String publisherName) {
List<Publisher> publishers = publisherDao.findAll();
Publisher foundPublisher = new Publisher();
for (Publisher publisher : publishers) {
if(publisher.getName().equals(publisherName)){
foundPublisher = publisher;
}
}
return foundPublisher;
}
}
在这里我调用函数:createGame()包括:
private void createGame(String name, String genreName, String publisherName) {
Game game = new Game();
game.setName(name);
Genre genre = new Genre();
genre.setName(genreName);
Publisher publisher;
if (manager.getPublisherByName(publisherName).getId() == null) {
publisher = new Publisher();
publisher.setName(publisherName);
} else {
publisher = manager.getPublisherByName(publisherName);
}
Set<Game> games = new HashSet<Game>();
games.add(game);
game.setPublisher(publisher);
games.addAll(publisher.getGames());
publisher.setGames(games);
manager.savePublisher(publisher);
manager.saveGame(game);
manager.saveGenre(genre);
}
第一次运行此功能时一切都很好。数据将持久存储到数据库中。但是,如果我运行它一段时间,我会收到此错误:
javax.ejb.EJBException:javax.persistence.PersistenceException:org.hibernate.PersistentObjectException:传递给persist的分离实体:de.fhb.rangam.data.Publisher
以及其他一些长篇文章,但这并不重要。
我没有得到的是为什么游戏获得Persiste和流派。发布应该更新? 我得到的错误,请帮忙!
很抱歉,如果已经有答案,我没有找到它,只是在我花了大约2天通过爬网找到解决方案之后再问。
答案 0 :(得分:0)
合并也可以插入或更新..在您的情况下,我认为最好删除条件if (game.getId() == null)
,并始终调用将插入和更新的update
..
差异是:
Persist接受一个实体实例,将其添加到上下文并使该实例得到管理(即将跟踪该实体的未来更新)。
Merge创建实体的新实例,从提供的实体复制状态,并管理新副本。您传入的实例将不会被管理(您所做的任何更改都不会成为交易的一部分 - 除非您再次调用合并)。
希望有所帮助