317 votes

Comment mettre à jour une entité en utilisant spring-data-jpa ?

La question dit à peu près tout. En utilisant JPARepository, comment mettre à jour une entité ?

JPARepository n'a qu'un sauver ce qui ne me permet pas de savoir s'il s'agit d'une création ou d'une mise à jour. Par exemple, j'insère un simple objet dans la base de données User, qui comporte trois champs : firstname , lastname et age :

 @Entity
 public class User {

  private String firstname;
  private String lastname;
  //Setters and getters for age omitted, but they are the same as with firstname and lastname.
  private int age;

  @Column
  public String getFirstname() {
    return firstname;
  }
  public void setFirstname(String firstname) {
    this.firstname = firstname;
  }

  @Column
  public String getLastname() {
    return lastname;
  }
  public void setLastname(String lastname) {
    this.lastname = lastname;
  }

  private long userId;

  @Id
  @GeneratedValue(strategy=GenerationType.AUTO)
  public long getUserId(){
    return this.userId;
  }

  public void setUserId(long userId){
    this.userId = userId;
  }
}

Ensuite, j'appelle simplement save() qui, à ce stade, est en fait une insertion dans la base de données :

 User user1 = new User();
 user1.setFirstname("john"); user1.setLastname("dew");
 user1.setAge(16);

 userService.saveUser(user1);// This call is actually using the JPARepository: userRepository.save(user);

Jusqu'à présent, tout va bien. Maintenant, je veux mettre à jour cet utilisateur, par exemple changer son âge. Pour ce faire, je pourrais utiliser une requête, soit QueryDSL ou NamedQuery, peu importe. Mais, étant donné que je veux juste utiliser spring-data-jpa et le JPARepository, comment puis-je lui dire qu'au lieu d'une insertion, je veux faire une mise à jour ?

Plus précisément, comment puis-je dire à spring-data-jpa que les utilisateurs ayant le même nom d'utilisateur et le même prénom sont en fait ÉGAUX et que l'entité existante est censée être mise à jour ? La surcharge de equals n'a pas résolu ce problème.

9voto

smile Points 174

Utilisation de spring-data-jpa save() J'ai eu le même problème que @DtechNet. Je veux dire que chaque save() créait un nouvel objet au lieu d'une mise à jour. Pour résoudre ce problème, j'ai dû ajouter version à l'entité et à la table connexe.

8voto

Adam Points 639

Voici comment j'ai résolu le problème :

User inbound = ...
User existing = userRepository.findByFirstname(inbound.getFirstname());
if(existing != null) inbound.setId(existing.getId());
userRepository.save(inbound);

4voto

Javid Points 135

Avec Java 8, vous pouvez utiliser findById du référentiel dans UserService

@Service
public class UserServiceImpl {

    private final UserRepository repository;

    public UserServiceImpl(UserRepository repository) {
        this.repository = repository;
    }

    @Transactional
    public void update(User user) {
        repository
                .findById(user.getId()) // returns Optional<User>
                .ifPresent(user1 -> {
                    user1.setFirstname(user.getFirstname);
                    user1.setLastname(user.getLastname);

                    repository.save(user1);
                });
    }

}

2voto

BinLee Points 29
public void updateLaserDataByHumanId(String replacement, String humanId) {
    List<LaserData> laserDataByHumanId = laserDataRepository.findByHumanId(humanId);
    laserDataByHumanId.stream()
            .map(en -> en.setHumanId(replacement))
            .collect(Collectors.toList())
            .forEach(en -> laserDataRepository.save(en));
}

1voto

Andreas Gelever Points 117

Plus précisément, comment puis-je indiquer à spring-data-jpa que les utilisateurs qui ont l'attribut le même nom d'utilisateur et le même prénom sont en fait ÉGAUX et qu'il est censé mettre à jour l'entité. mettre à jour l'entité. La surcharge de equals n'a pas fonctionné.

À cette fin, on peut introduire une clé composite comme suit :

CREATE TABLE IF NOT EXISTS `test`.`user` (
  `username` VARCHAR(45) NOT NULL,
  `firstname` VARCHAR(45) NOT NULL,
  `description` VARCHAR(45) NOT NULL,
  PRIMARY KEY (`username`, `firstname`))

Cartographie :

@Embeddable
public class UserKey implements Serializable {
    protected String username;
    protected String firstname;

    public UserKey() {}

    public UserKey(String username, String firstname) {
        this.username = username;
        this.firstname = firstname;
    }
    // equals, hashCode
}

Voici comment l'utiliser :

@Entity
public class UserEntity implements Serializable {
    @EmbeddedId
    private UserKey primaryKey;

    private String description;

    //...
}

JpaRepository ressemblerait à ceci :

public interface UserEntityRepository extends JpaRepository<UserEntity, UserKey>

Dans ce cas, vous pouvez utiliser ce qui suit idiome : accepter le DTO avec les informations de l'utilisateur, extraire le nom et le prénom et créer une UserKey, puis créer une UserEntity avec cette clé composite et ensuite invoquer Spring Data save() qui devrait tout régler pour vous.

Prograide.com

Prograide est une communauté de développeurs qui cherche à élargir la connaissance de la programmation au-delà de l'anglais.
Pour cela nous avons les plus grands doutes résolus en français et vous pouvez aussi poser vos propres questions ou résoudre celles des autres.

Powered by:

X