jden
jden

Reputation: 2288

JPA OneToOne UPDATE instead of INSERT

I am new to Spring/JPA and I am trying to use Database relationship @annotations to simplify my code.

I have two entities, a User and Token entity. When setToken() is called on the User, I want the Token to overwrite any old tokens associated with the user in the table.

At the moment, the new token (via user.setToken()) is being INSERT rather than UPDATE.

How do I go about achieving this relationship? In "Lame-mans"...A user can only even have one token and can be given another at any time, discarding the old. There are extra fields in these models that i have truncated for clarity.

@Entity
@Table(name = "Users")
public class User {

    @Column(name = "USER_ID")
    @Id @GeneratedValue(strategy = GenerationType.IDENTITY)
    @JsonInclude(JsonInclude.Include.NON_NULL)
    private Long userId;

    @OneToOne(fetch = FetchType.LAZY,cascade = CascadeType.ALL)
    @JoinColumn(name = "REFRESH_TOKEN_ID")
    private RefreshToken refreshToken;

...setters and getters

And the code for a token:

@Entity
@Table(name = "RefreshTokens")
public class RefreshToken {

    @Column(name = "REFRESH_TOKEN_ID")
    @Id @GeneratedValue(strategy = GenerationType.IDENTITY)
    private Long tokenId;

Upvotes: 1

Views: 1670

Answers (2)

MyTwoCents
MyTwoCents

Reputation: 7624

If your RefreshToken has only 1 Field REFRESH_TOKEN_ID which is long. Why you need different table for this. You can just have something like this

public class User {

    @Column(name = "USER_ID")
    @Id @GeneratedValue(strategy = GenerationType.IDENTITY)
    @JsonInclude(JsonInclude.Include.NON_NULL)
    private Long userId;

    @Column(name = "REFRESH_TOKEN_ID")
    private Long refreshToken;

...

When setToken() is called you must be setting any value. If yes thats it. Your logic will work fine,

If no you can always generate a Unique value in Java based on Current time or something else.

or

If you want to continue with same patter use orphanRemoval = true

@OneToOne(fetch = FetchType.LAZY,cascade = CascadeType.ALL, orphanRemoval = true)
@JoinColumn(name = "REFRESH_TOKEN_ID")
private RefreshToken refreshToken;

Upvotes: 2

Ilias Mentz
Ilias Mentz

Reputation: 520

You should never modify the primary key of a an entity

This is not be possible as you change the id of the token. You need to create a different id in the RefreshToken thats unique and stays the same after save.

If you really do need that - you'd better of delete the entity and create a new one which just copies the old one but with a new primary key.

Upvotes: 0

Related Questions