从org.springframework.data.jpa.repository.support.SimpleJpaRepository中的findAll返回重复项

时间:2018-10-19 22:02:56

标签: java spring hibernate spring-data-jpa

所以我的存储库定义如下:

public interface PersonRepository extends CrudRepository<Person, Long>

我的实体如下:

@Entity
@Table(name="Person")
public class Person implements Serializable {

private static final long serialVersionUID = 1L;

@Id
@SequenceGenerator(name="PERSON_GENERATOR", sequenceName="PERSON_SEQ")
@GeneratedValue(strategy=GenerationType.SEQUENCE, generator="PERSON_GENERATOR")
private Long id;

@Column(name="ssn")
private String socialSecurityNumber;

private String name;
public Person() {
}

public Long getId() {
    return this.id;
}

public void setId(Long id) {
    this.id = id;
}

我省略了socialSecurityNumber和Name的获取器和设置器。数据库中有1000条记录。

我有一个注有@Component的Spring bean,它通过调用PersonRepo findAll()使用PersonRepo。当findAll()被调用时,我会得到1000条带有其唯一ID的记录的列表,当我遍历findAll()返回的人员列表时,会发现意外的结果。

@Component
public class PersonComponent {

    @Autowired
    PersonRepository personRepo;

    public void printPerson() {
        List<Person> people = personRepo.findAll();
        for(Person person : people) {
            System.out.println("id=" + person.getId() + ", ssn=" + person.getSocialSecurityNumber() + ", name=" + person.getName());
        }
    }
}

所以,如果在我的数据库中,我有记录

id, ssn,  name
 1, ssn1, Bob
 2, ssn2, Mary
 3, ssn3, Joe

当我打电话给findAll()时,我会不断地找回它

id=1, ssn=ssn1, name=Bob
id=2, ssn=ssn2, name=Mary
id=3, ssn=ssn2, name=Mary

请注意,我获得了正确的ID(即1、2、3),但由于某种原因,id 3映射到了ssn2,Mary而非NOT ssn3,Joe

此行为仅在第一次调用findAll()之后发生(即,第一个findAll可以正常工作,但随后一次显示上述行为)。换句话说,当应用程序启动并且使用PersonRepo的Spring bean首次被调用时,findAll()似乎可以正常工作。但是,当对Spring Bean进行后续调用时,findAll的行为将如上所述。

最后,当我调用Web服务http://localhost/persons(在幕后调用`findAll())时,每次都会得到正确的行为。

有什么想法吗?

1 个答案:

答案 0 :(得分:0)

问题可能与省略姓名和社会保障变量的获取器和设置器有关?在将所有这些声明为私有之后,我们需要一种方法来访问它们,因此为什么要使用吸气剂?

我已经复制了您的应用,如果您使用以下内容,则根本不会出现重复的情况。

Appllication.properties文件:

spring.jpa.hibernate.ddl-auto=update
spring.datasource.url=jdbc:mysql://localhost:3306/findall_db
spring.datasource.username=YOUR_DATABASE_USERNAME
spring.datasource.password=YOUR_DATABASE_PASSWORD

人实体Java类:

package com.example.demo;

import java.io.Serializable;

import javax.persistence.Column;
import javax.persistence.Entity;
import javax.persistence.GeneratedValue;
import javax.persistence.GenerationType;
import javax.persistence.Id;
import javax.persistence.SequenceGenerator;
import javax.persistence.Table;

@Entity
@Table(name="Person")
public class PersonInfo implements Serializable {

private static final long serialVersionUID = 1L;

@Id
@SequenceGenerator(name="PERSON_GENERATOR", sequenceName="PERSON_SEQ")
@GeneratedValue(strategy=GenerationType.SEQUENCE, generator="PERSON_GENERATOR")
private Long id;

@Column(name="ssn")
private String socialSecurityNumber;

private String name;



public PersonInfo() {
}



public Long getId() {
    return id;
}



public void setId(Long id) {
    this.id = id;
}



public String getSocialSecurityNumber() {
    return socialSecurityNumber;
}



public void setSocialSecurityNumber(String socialSecurityNumber) {
    this.socialSecurityNumber = socialSecurityNumber;
}



public String getName() {
    return name;
}



public void setName(String name) {
    this.name = name;
}



@Override
public String toString() {
    return "PersonInfo [id=" + id + ", socialSecurityNumber=" + socialSecurityNumber + ", name=" + name + "]";
}

}

人员存储库:

package com.example.demo;

import org.springframework.data.repository.CrudRepository;
import org.springframework.stereotype.Repository;

@Repository
public interface PersonInfoRepository extends CrudRepository<PersonInfo, Long>{

}

人控:

package com.example.demo;

import java.util.List;

import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Controller;
import org.springframework.web.bind.annotation.GetMapping;
import org.springframework.web.bind.annotation.ResponseBody;
import org.springframework.web.bind.annotation.RestController;

@Controller
public class PersonController {

    @Autowired
    PersonInfoRepository personRepo;


    @ResponseBody
    @GetMapping("/people")
    public List printPersonInfo() {

           List<PersonInfo> people = (List<PersonInfo>) personRepo.findAll();

           System.out.println(people.toString());

    return people ;

}   


}