Spring JPA creates new record instead of updating existing record

Viewed 2436

I am using standard Spring CrudRepository. When attempting to update a record, a new record is created instead even though the primary key is assigned a non-null value.

Any suggestions on what I'm doing wrong?

Thanks, Timothy

Software versions

  • Spring boot 2.4.0
  • Database postgres 9.6.17

Entity to be saved

@Entity
@Table(name = "dc_motor")
public class DcMotor implements Serializable, DatabaseEntity {
    private static final long serialVersionUID = 4015060163435939638L;

    @Id
    @GeneratedValue(strategy = GenerationType.IDENTITY)
    private Long id;
    @Version
    private Integer version;
    // other fields here
    // does NOT define equals() nor hashCode()
}

save method in service tier

@Override
    public DcMotorRest saveMotor(DcMotorRest motorToBeSaved) throws MotorNotFoundException {
        if (motorToBeSaved.getId() != null) {

            Optional<DcMotor> motor = dcRepo.findById(motorToBeSaved.getId());

            if (!motor.isPresent())
                throw new MotorNotFoundException(
                        "DC Motor with ID [%d] not found.  Unable to update.  Use empty / null id to create a new DC Motor"
                                .formatted(motorToBeSaved.getId()));
        }

        // troubleshooting code
        DcMotor t = new DcMotor(motorToBeSaved);
        if (t.getId() == null) {
            logger.debug("ID is null in motor to be saved");
        } else {
            logger.debug("ID is [{}] in motor to be saved", t.getId());
        }
        DcMotor savedMotor = dcRepo.save(t);    // dcRepo extends CrudRepository<DcMotor, Long>

        // DcMotor savedMotor = new DcMotor(motorToBeSaved);

        return new ModelMapper().map(savedMotor, DcMotorRest.class);
    }

Log output

  DEBUG 7868 --- [nio-8070-exec-1] c.e.s.w.service.impl.DcMotorServiceImpl  : ID is [2333] in motor to be saved
  DEBUG 7868 --- [nio-8070-exec-1] org.hibernate.SQL                        : insert into dc_motor ( ...) values (...)
2 Answers

Yes, the problem is here:

DcMotor t = new DcMotor(motorToBeSaved);

Basically it's an object you create, Hibernate doesn't know about it so it's considered as a new object. You need to first find that entity in the database, update it and then save.

Related