Obtain an entity, assign it and save it again

0

I have a system where I have users and each one can have several roles.

@Entity
@Table(
        uniqueConstraints=
            @UniqueConstraint(columnNames={"username"})
    )
public class CustomUser implements UserDetails {
    private static final long serialVersionUID = 1L;
    @Id @GeneratedValue(strategy = GenerationType.IDENTITY)
    private Long id;
    private String username;
    private String password;
    private String email;
    private String firstName;
    private String lastName;

    /* Spring Security related fields*/
    @OneToMany(fetch = FetchType.EAGER)
    private List<Role> authorities;
    [...]
}

I receive a user to add along with their roles, which, to avoid having to repeatedly save the same role in the database, what I do is obtain it from the database, if it does not exist, I add it, and if there is, assign it to my user.

private List<Role> getRoles(List<Role> userAuthorities) {
    List<Role> newRoles = new ArrayList<Role>(); // Lista con los nombres de los roles

    // Busco si existe, y si no existen los agrego
    for (Role role : userAuthorities) {
        Role existingRole = this.getRoleRepository().findOneByName(role.getName()).orElse(null);
        // Si no existe lo agrego
        if (existingRole == null) {
            this.getRoleRepository().save(role);
            newRoles.add(role);
        } else {
            newRoles.add(existingRole);
        }
    }

    return newRoles;
}

@Override
public CustomUserDTO create(CustomUserDTO userDto) {
    List<Role> roles = this.getRoles(userDto.getAuthorities());
    CustomUser user = this.getTransformer().toEntity(userDto);
    user.setAuthorities(roles); // Asigno los roles

    this.getUserRepository().save(user);
    return this.getTransformer().toDTO(user); // Devuelvo a DTO el usuario recien creado
}

When I raise a user whose role is not yet in the DB there is no problem. But when it exists in the DB, I assign it to my user and I save it to the latter. I get the following error:

  

"could not execute statement; SQL [n / a]; constraint   ["UK_735R7F0TONHSBGBPXMMRRC0MS_INDEX_8 ON   PUBLIC.CUSTOM_USER_AUTHORITIES (AUTHORITIES_ID) VALUES (3, 3) "; SQL   statement: insert into custom_user_authorities (custom_user_id,   authorities_id) values (?,?) [23505-197]]; nested exception is   org.hibernate.exception.ConstraintViolationException: could not   execute statement "

That is, you are trying to insert the role with the same ID again and there it breaks.

How can I get the existing role to reuse it, assign it to my user, save that user without exploiting it?

Thank you very much

    
asked by Genarito 20.07.2018 в 05:15
source

0 answers