【问题标题】:Update row in DB by other unique value instead primary key using Hibernate?通过其他唯一值而不是使用 Hibernate 的主键更新 DB 中的行?
【发布时间】:2019-04-05 13:51:45
【问题描述】:

我正在编写 REST Web 服务。我创建下一个作者实体:

@Entity
@Table(name = "author")
public class Author {

    @Id
    @GeneratedValue(strategy = GenerationType.IDENTITY)
    @Column(name = "id")
    private int id;

    @Column(name = "authorId", unique = true, nullable = false)
    private int authorId;

    @Column(name = "authorName", nullable = false)
    private String name;

    @Column(name = "authorSurname")
    private String surname;

    @Column(name = "nationality")
    private String nationality;

    @Column(name = "age")
    private int age;

    @OneToMany(mappedBy = "author", cascade = CascadeType.ALL)
    private List<Book> bookList;

    public Author() {
    }

    public Author(int authorId, String name, String surname, String nationality, int age) {
        this.authorId = authorId;
        this.name = name;
        this.surname = surname;
        this.nationality = nationality;
        this.age = age;
    }
}

DB 中的id 值在 DB 中使用类似主键来引用其他表。对于通过 URL 识别实体(如 /rest/Author/{authorId}),请使用其他值 - authorId。我也没有在实体构造函数中使用它。 DAO updateAuthor 方法如下所示:

public Author updateAuthor(Author author) {
    Session session = getSessionFactory().openSession();
    Transaction transaction = session.beginTransaction();
    session.update(author);
    transaction.commit();

    Author updated = (Author) session
            .createQuery("FROM Author WHERE authorId=" + author.getAuthorId())
            .uniqueResult();

    session.close();
    return updated;
}

但它无法正常工作...当我尝试使用 authorId = 4 更新现有实体时:

Author author1 = authorDao.updateAuthor(new Author(4, "qweqwe", "qweqwe", "qweqwe", 1000));

获取下一个执行的 HQL 查询:

Hibernate: update author set age=?, authorId=?, authorName=?, nationality=?, authorSurname=? where id=?

还有下一个例外:

Exception in thread "main" org.hibernate.StaleStateException: Batch update returned unexpected row count from update [0]; actual row count: 0; expected: 1

如何在不单独设置所有值的情况下解决此问题??

【问题讨论】:

  • 再次确定,您能发布Author 构造函数吗?
  • @lealceldeiro,将其添加到问题正文中
  • 您确定在您尝试更新的给定作者对象上设置了 id 吗?如果不是,那么 where 子句会说 id = null 并且不会有 id 为 null 的行,因此更新查询不会影响表中的任何行
  • 好吧,这里似乎session.update(author); 肯定是在尝试基于id 属性进行更新(0,因为它不是默认设置的)并且没有将authorId 作为更新的参考具有用于构造传递的Author 的 id 的现有作者。

标签: java sql hibernate web-services dao


【解决方案1】:

你可以试试这个 你的:

@Id
@GeneratedValue(strategy = GenerationType.IDENTITY)
@Column(name = "id")
private int id;

换成这个试试

@Column(name = "id", updatable = false, nullable = false)

【讨论】:

    【解决方案2】:

    我找到了解决办法!

    只需从 Author 模型中删除 id 属性并将 @Id 注释粘贴到 authorId 值上:

    @Entity
    @Table(name = "author")
    public class Author {
    
        @Id
        @Column(name = "authorId", unique = true, nullable = false)
        private int authorId;
    
        @Column(name = "authorName", nullable = false)
        private String name;
    
        @Column(name = "authorSurname")
        private String surname;
    
        @Column(name = "nationality")
        private String nationality;
    
        @Column(name = "age")
        private int age;
    
        @OneToMany(mappedBy = "author", cascade = CascadeType.ALL)
        private List<Book> bookList;
    
        public Author(){
        }
    
        public Author(int authorId, String name, String surname, String nationality, int age) {
            this.authorId = authorId;
            this.name = name;
            this.surname = surname;
            this.nationality = nationality;
            this.age = age;
        }
    }
    

    所以现在 Hibarnate 得到 id 正好是 authorId。 现在可以正常使用了。

    【讨论】:

      猜你喜欢
      • 2022-01-02
      • 1970-01-01
      • 1970-01-01
      • 2016-06-07
      • 1970-01-01
      • 2012-09-02
      • 1970-01-01
      • 1970-01-01
      • 2023-02-16
      相关资源
      最近更新 更多