简体   繁体   中英

Invalid custom update query defined in Spring Data JPA CrudRepository

I have a custom JPQL query in a Spring CrudRepository that's not working.

This is my entity class, PK class and CrudRepository interface for the entity:

@Entity(name = "TBL_PRINCIPAL_CREDENTIAL")
public class PrincipalCredential {

    @EmbeddedId
    private PrincipalCredentialPK principalCredentialPK;

    // ...getter & setter for principalCredentialPK
}

@Embeddable
public class PrincipalCredentialPK implements Serializable {

    @Column(name = "PRINCIPAL_TYPE_ID", nullable = false)
    private String principalTypeID;

    @Column(name = "PRINCIPAL_ID", nullable = false)
    private String principalID;

    @Column(name = "CREDENTIAL_ID", nullable = false)
    private Integer credentialID;

    @Column(name = "CREDENTIAL_TYPE_ID", nullable = false)
    private String credentialTypeID;

    // ...getters & setters for all fields...
}

@Transactional
public interface PrincipalCredentialRepository extends CrudRepository<PrincipalCredential, PrincipalCredentialPK> {

    @Modifying
    @Query("update PrincipalCredential pc set pc.principalCredentialPK.principalID =:newPrincipalID " +
            "where pc.principalCredentialPK.principalID =:oldPrincipalID and pc.principalCredentialPK.principalTypeID =:principalType")
    void updatePrincipalID(@Param("oldPrincipalID") String oldPrincipalID, @Param("newPrincipalID") String newPrincipalID,
                           @Param("principalType") String principalType);
}

When I start my project using SpringBoot the repository bean cannot be instantiated and I get the following exception:

Caused by: org.springframework.beans.factory.BeanCreationException: Error creating bean with name 'principalCredentialRepository': Invocation of init method failed; nested exception is java.lang.IllegalArgumentException: Validation failed for query for method public abstract void com.consorsbank.services.banking.caas.repositories.PrincipalCredentialRepository.updatePrincipalID(java.lang.String,java.lang.String,java.lang.String)!

Caused by: java.lang.IllegalArgumentException: Validation failed for query for method public abstract void com.consorsbank.services.banking.caas.repositories.PrincipalCredentialRepository.updatePrincipalID(java.lang.String,java.lang.String,java.lang.String)!

Caused by: java.lang.IllegalArgumentException: org.hibernate.hql.internal.ast.QuerySyntaxException: PrincipalCredential is not mapped [update PrincipalCredential pc set pc.principalCredentialPK.principalID =:newPrincipalID where pc.principalCredentialPK.principalID =:oldPrincipalID and pc.principalCredentialPK.principalTypeID =:principalType]

Also for another repository this query is working, the difference is that the PK of the other entity is simpler and both ids are provided there...

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

    @EmbeddedId
    private PrincipalPK principalPK;

    @OneToOne
    @JoinColumn(name = "PRINCIPAL_TYPE_ID", insertable = false, updatable = false)
    private PrincipalType principalType;

    @Column(name = "USER_ID")
    private Integer userID;

    @Column(name = "VALID_UNTIL")
    private Date validUntil;

    @OneToMany(cascade = CascadeType.ALL, fetch = FetchType.EAGER)
    @JoinTable(name = "ZAAS_TBL_PRINCIPAL_CREDENTIAL",
            joinColumns = {@JoinColumn(name = "PRINCIPAL_ID"), @JoinColumn(name = "PRINCIPAL_TYPE_ID")},
            inverseJoinColumns = {@JoinColumn(name = "CREDENTIAL_ID"), @JoinColumn(name="CREDENTIAL_TYPE_ID")})
    public Set<Credential> credentials;

    // ...getters and setters...
}

@Embeddable
public class PrincipalPK implements Serializable {

    @Column(name = "PRINCIPAL_TYPE_ID", nullable = false)
    private String principalTypeID;

    @Column(name = "PRINCIPAL_ID", nullable = false)
    private String principalID;

    // ...getters and setters
}

@Transactional
public interface PrincipalsRepository extends CrudRepository<Principal, PrincipalPK> {

    @Modifying
    @Query("update Principal p set p.principalPK.principalID =:newPrincipalID " +
            "where p.principalPK.principalID =:oldPrincipalID and p.principalPK.principalTypeID =:principalType")
    void updatePrincipalID(@Param("oldPrincipalID") String oldPrincipalID, @Param("newPrincipalID") String newPrincipalID,
                           @Param("principalType") String principalType);
}

So the above query is working... Could someone please point out what I'm missing for the query defined in the PrincipalCredentialRepository?

The entity definition seems to be wrong. Use the following annotations

@Entity
@Table(name = "TBL_PRINCIPAL_CREDENTIAL")
public class PrincipalCredential {
//...

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM