【问题标题】:Hibernate StackOverflowError with @OneToMany and @ManyToOne mapping使用 @OneToMany 和 @ManyToOne 映射的 Hibernate StackOverflowError
【发布时间】:2019-05-06 16:47:13
【问题描述】:

实体

我有三个实体UserPermissionUserPermission

[User] --(OneToMany)--> [UserPermission]
[UserPermission] --(ManyToOne)--> [User]
[UserPermission] --(ManyToOne)--> [Permission]

这些是简化的实现:

@Entity
@JsonIgnoreProperties({ "hibernateLazyInitializer", "handler" })
@NoArgsConstructor @RequiredArgsConstructor @AllArgsConstructor
public class User {
    @Id
    @NonNull @NotNull
    private String id;

    // ... Other non pk fields

    @JsonIgnore
    @OneToMany(cascade = CascadeType.ALL, fetch = FetchType.LAZY)
    @JoinColumn(name = "user", referencedColumnName = "id")
    private Collection<UserPermission> permissions;
}
@Entity @IdClass(UserPermission.PK.class)
@JsonIgnoreProperties({ "hibernateLazyInitializer", "handler" })
@NoArgsConstructor @AllArgsConstructor @RequiredArgsConstructor
public class UserPermission {
    @Id @NonNull @NotNull
    @ManyToOne
    @JoinColumn(name = "user", updatable = false, insertable = false)
    private User user;

    @Id @NonNull @NotNull
    @ManyToOne
    @JoinColumn(name = "permission", updatable = false, insertable = false)
    private Permission permission;

    // ... Other non pk fields

    @Getter @Setter @NoArgsConstructor @AllArgsConstructor
    public static class PK implements Serializable {
        private User user;

        private Permission permission;
    }
}
@Entity
@JsonIgnoreProperties({ "hibernateLazyInitializer", "handler" })
@NoArgsConstructor @AllArgsConstructor @RequiredArgsConstructor
public class Permission {
    @Id
    @NonNull @NotNull
    private String id;

    // ... Other non pk fields
}

问题

当我尝试使用org.springframework.data.repository.CrudRepository.save(S) 方法更新UserPermission 时:

@Override
public T upd(ID id, T entity) {
    entity.setPk(id);
    return repository.save(entity);
}

我得到以下异常:

java.lang.StackOverflowError: null
    at java.lang.Character.isWhitespace(Character.java:6789) ~[na:1.8.0_151]
    at java.lang.Character.isWhitespace(Character.java:6757) ~[na:1.8.0_151]
    at org.postgresql.core.Parser.parseJdbcSql(Parser.java:82) ~[postgresql-42.2.5.jar:42.2.5]
    at org.postgresql.core.CachedQueryCreateAction.create(CachedQueryCreateAction.java:63) ~[postgresql-42.2.5.jar:42.2.5]
    at org.postgresql.core.CachedQueryCreateAction.create(CachedQueryCreateAction.java:17) ~[postgresql-42.2.5.jar:42.2.5]
    at org.postgresql.util.LruCache.borrow(LruCache.java:115) ~[postgresql-42.2.5.jar:42.2.5]
    at org.postgresql.core.QueryExecutorBase.borrowQuery(QueryExecutorBase.java:271) ~[postgresql-42.2.5.jar:42.2.5]
    at org.postgresql.jdbc.PgConnection.borrowQuery(PgConnection.java:146) ~[postgresql-42.2.5.jar:42.2.5]
    at org.postgresql.jdbc.PgPreparedStatement.<init>(PgPreparedStatement.java:78) ~[postgresql-42.2.5.jar:42.2.5]
    at org.postgresql.jdbc.PgConnection.prepareStatement(PgConnection.java:1223) ~[postgresql-42.2.5.jar:42.2.5]
    at org.postgresql.jdbc.PgConnection.prepareStatement(PgConnection.java:1681) ~[postgresql-42.2.5.jar:42.2.5]
    at org.postgresql.jdbc.PgConnection.prepareStatement(PgConnection.java:371) ~[postgresql-42.2.5.jar:42.2.5]
    at com.zaxxer.hikari.pool.ProxyConnection.prepareStatement(ProxyConnection.java:311) ~[HikariCP-3.2.0.jar:na]
    at com.zaxxer.hikari.pool.HikariProxyConnection.prepareStatement(HikariProxyConnection.java) ~[HikariCP-3.2.0.jar:na]
    at org.hibernate.engine.jdbc.internal.StatementPreparerImpl$5.doPrepare(StatementPreparerImpl.java:146) ~[hibernate-core-5.3.7.Final.jar:5.3.7.Final]
    at org.hibernate.engine.jdbc.internal.StatementPreparerImpl$StatementPreparationTemplate.prepareStatement(StatementPreparerImpl.java:172) ~[hibernate-core-5.3.7.Final.jar:5.3.7.Final]
    at org.hibernate.engine.jdbc.internal.StatementPreparerImpl.prepareQueryStatement(StatementPreparerImpl.java:148) ~[hibernate-core-5.3.7.Final.jar:5.3.7.Final]
    at org.hibernate.loader.Loader.prepareQueryStatement(Loader.java:1984) ~[hibernate-core-5.3.7.Final.jar:5.3.7.Final]
    at org.hibernate.loader.Loader.executeQueryStatement(Loader.java:1914) ~[hibernate-core-5.3.7.Final.jar:5.3.7.Final]
    at org.hibernate.loader.Loader.executeQueryStatement(Loader.java:1892) ~[hibernate-core-5.3.7.Final.jar:5.3.7.Final]
    at org.hibernate.loader.Loader.doQuery(Loader.java:937) ~[hibernate-core-5.3.7.Final.jar:5.3.7.Final]
    at org.hibernate.loader.Loader.doQueryAndInitializeNonLazyCollections(Loader.java:340) ~[hibernate-core-5.3.7.Final.jar:5.3.7.Final]
    at org.hibernate.loader.Loader.doQueryAndInitializeNonLazyCollections(Loader.java:310) ~[hibernate-core-5.3.7.Final.jar:5.3.7.Final]
    at org.hibernate.loader.Loader.loadEntity(Loader.java:2281) ~[hibernate-core-5.3.7.Final.jar:5.3.7.Final]
    at org.hibernate.loader.entity.AbstractEntityLoader.load(AbstractEntityLoader.java:64) ~[hibernate-core-5.3.7.Final.jar:5.3.7.Final]
    at org.hibernate.loader.entity.AbstractEntityLoader.load(AbstractEntityLoader.java:54) ~[hibernate-core-5.3.7.Final.jar:5.3.7.Final]
    at org.hibernate.persister.entity.AbstractEntityPersister.load(AbstractEntityPersister.java:4269) ~[hibernate-core-5.3.7.Final.jar:5.3.7.Final]
    at org.hibernate.event.internal.DefaultLoadEventListener.loadFromDatasource(DefaultLoadEventListener.java:511) ~[hibernate-core-5.3.7.Final.jar:5.3.7.Final]
    at org.hibernate.event.internal.DefaultLoadEventListener.doLoad(DefaultLoadEventListener.java:481) ~[hibernate-core-5.3.7.Final.jar:5.3.7.Final]
    at org.hibernate.event.internal.DefaultLoadEventListener.load(DefaultLoadEventListener.java:222) ~[hibernate-core-5.3.7.Final.jar:5.3.7.Final]
    at org.hibernate.event.internal.DefaultLoadEventListener.proxyOrLoad(DefaultLoadEventListener.java:281) ~[hibernate-core-5.3.7.Final.jar:5.3.7.Final]
    at org.hibernate.event.internal.DefaultLoadEventListener.doOnLoad(DefaultLoadEventListener.java:124) ~[hibernate-core-5.3.7.Final.jar:5.3.7.Final]
    at org.hibernate.event.internal.DefaultLoadEventListener.onLoad(DefaultLoadEventListener.java:92) ~[hibernate-core-5.3.7.Final.jar:5.3.7.Final]
    at org.hibernate.internal.SessionImpl.fireLoad(SessionImpl.java:1257) ~[hibernate-core-5.3.7.Final.jar:5.3.7.Final]
    at org.hibernate.internal.SessionImpl.internalLoad(SessionImpl.java:1140) ~[hibernate-core-5.3.7.Final.jar:5.3.7.Final]

    at org.hibernate.type.EntityType.resolveIdentifier(EntityType.java:682) ~[hibernate-core-5.3.7.Final.jar:5.3.7.Final]
    at org.hibernate.type.EntityType.resolve(EntityType.java:464) ~[hibernate-core-5.3.7.Final.jar:5.3.7.Final]
    at org.hibernate.type.ManyToOneType.resolve(ManyToOneType.java:239) ~[hibernate-core-5.3.7.Final.jar:5.3.7.Final]
    at org.hibernate.type.EntityType.resolve(EntityType.java:457) ~[hibernate-core-5.3.7.Final.jar:5.3.7.Final]
    at org.hibernate.type.ComponentType.resolve(ComponentType.java:688) ~[hibernate-core-5.3.7.Final.jar:5.3.7.Final]
    at org.hibernate.loader.Loader.extractKeysFromResultSet(Loader.java:862) ~[hibernate-core-5.3.7.Final.jar:5.3.7.Final]
    at org.hibernate.loader.Loader.getRowFromResultSet(Loader.java:718) ~[hibernate-core-5.3.7.Final.jar:5.3.7.Final]
    at org.hibernate.loader.Loader.processResultSet(Loader.java:990) ~[hibernate-core-5.3.7.Final.jar:5.3.7.Final]

    at org.hibernate.loader.Loader.doQuery(Loader.java:948) ~[hibernate-core-5.3.7.Final.jar:5.3.7.Final]

    at org.hibernate.loader.Loader.doQueryAndInitializeNonLazyCollections(Loader.java:340) ~[hibernate-core-5.3.7.Final.jar:5.3.7.Final]
    at org.hibernate.loader.Loader.doQueryAndInitializeNonLazyCollections(Loader.java:310) ~[hibernate-core-5.3.7.Final.jar:5.3.7.Final]
    at org.hibernate.loader.Loader.loadEntity(Loader.java:2281) ~[hibernate-core-5.3.7.Final.jar:5.3.7.Final]
    at org.hibernate.loader.entity.AbstractEntityLoader.load(AbstractEntityLoader.java:64) ~[hibernate-core-5.3.7.Final.jar:5.3.7.Final]
    at org.hibernate.loader.entity.AbstractEntityLoader.load(AbstractEntityLoader.java:54) ~[hibernate-core-5.3.7.Final.jar:5.3.7.Final]
    at org.hibernate.persister.entity.AbstractEntityPersister.load(AbstractEntityPersister.java:4269) ~[hibernate-core-5.3.7.Final.jar:5.3.7.Final]
    at org.hibernate.event.internal.DefaultLoadEventListener.loadFromDatasource(DefaultLoadEventListener.java:511) ~[hibernate-core-5.3.7.Final.jar:5.3.7.Final]
    at org.hibernate.event.internal.DefaultLoadEventListener.doLoad(DefaultLoadEventListener.java:481) ~[hibernate-core-5.3.7.Final.jar:5.3.7.Final]
    at org.hibernate.event.internal.DefaultLoadEventListener.load(DefaultLoadEventListener.java:222) ~[hibernate-core-5.3.7.Final.jar:5.3.7.Final]
    at org.hibernate.event.internal.DefaultLoadEventListener.proxyOrLoad(DefaultLoadEventListener.java:281) ~[hibernate-core-5.3.7.Final.jar:5.3.7.Final]
    at org.hibernate.event.internal.DefaultLoadEventListener.doOnLoad(DefaultLoadEventListener.java:124) ~[hibernate-core-5.3.7.Final.jar:5.3.7.Final]
    at org.hibernate.event.internal.DefaultLoadEventListener.onLoad(DefaultLoadEventListener.java:92) ~[hibernate-core-5.3.7.Final.jar:5.3.7.Final]
    at org.hibernate.internal.SessionImpl.fireLoad(SessionImpl.java:1257) ~[hibernate-core-5.3.7.Final.jar:5.3.7.Final]
    at org.hibernate.internal.SessionImpl.internalLoad(SessionImpl.java:1140) ~[hibernate-core-5.3.7.Final.jar:5.3.7.Final]


    // Repeated over and over

    at org.hibernate.type.EntityType.resolveIdentifier(EntityType.java:682) ~[hibernate-core-5.3.7.Final.jar:5.3.7.Final]
    at org.hibernate.type.EntityType.resolve(EntityType.java:464) ~[hibernate-core-5.3.7.Final.jar:5.3.7.Final]
    at org.hibernate.type.ManyToOneType.resolve(ManyToOneType.java:239) ~[hibernate-core-5.3.7.Final.jar:5.3.7.Final]
    at org.hibernate.type.EntityType.resolve(EntityType.java:457) ~[hibernate-core-5.3.7.Final.jar:5.3.7.Final]
    at org.hibernate.type.ComponentType.resolve(ComponentType.java:688) ~[hibernate-core-5.3.7.Final.jar:5.3.7.Final]
    at org.hibernate.loader.Loader.extractKeysFromResultSet(Loader.java:862) ~[hibernate-core-5.3.7.Final.jar:5.3.7.Final]
    at org.hibernate.loader.Loader.getRowFromResultSet(Loader.java:718) ~[hibernate-core-5.3.7.Final.jar:5.3.7.Final]
    at org.hibernate.loader.Loader.processResultSet(Loader.java:990) ~[hibernate-core-5.3.7.Final.jar:5.3.7.Final]
    at org.hibernate.loader.Loader.doQuery(Loader.java:948) ~[hibernate-core-5.3.7.Final.jar:5.3.7.Final]
    at org.hibernate.loader.Loader.doQueryAndInitializeNonLazyCollections(Loader.java:340) ~[hibernate-core-5.3.7.Final.jar:5.3.7.Final]
    at org.hibernate.loader.Loader.doQueryAndInitializeNonLazyCollections(Loader.java:310) ~[hibernate-core-5.3.7.Final.jar:5.3.7.Final]
    at org.hibernate.loader.Loader.loadEntity(Loader.java:2281) ~[hibernate-core-5.3.7.Final.jar:5.3.7.Final]
    at org.hibernate.loader.entity.AbstractEntityLoader.load(AbstractEntityLoader.java:64) ~[hibernate-core-5.3.7.Final.jar:5.3.7.Final]
    at org.hibernate.loader.entity.AbstractEntityLoader.load(AbstractEntityLoader.java:54) ~[hibernate-core-5.3.7.Final.jar:5.3.7.Final]
    at org.hibernate.persister.entity.AbstractEntityPersister.load(AbstractEntityPersister.java:4269) ~[hibernate-core-5.3.7.Final.jar:5.3.7.Final]
    at org.hibernate.event.internal.DefaultLoadEventListener.loadFromDatasource(DefaultLoadEventListener.java:511) ~[hibernate-core-5.3.7.Final.jar:5.3.7.Final]
    at org.hibernate.event.internal.DefaultLoadEventListener.doLoad(DefaultLoadEventListener.java:481) ~[hibernate-core-5.3.7.Final.jar:5.3.7.Final]
    at org.hibernate.event.internal.DefaultLoadEventListener.load(DefaultLoadEventListener.java:222) ~[hibernate-core-5.3.7.Final.jar:5.3.7.Final]
    at org.hibernate.event.internal.DefaultLoadEventListener.proxyOrLoad(DefaultLoadEventListener.java:281) ~[hibernate-core-5.3.7.Final.jar:5.3.7.Final]
    at org.hibernate.event.internal.DefaultLoadEventListener.doOnLoad(DefaultLoadEventListener.java:124) ~[hibernate-core-5.3.7.Final.jar:5.3.7.Final]
    at org.hibernate.event.internal.DefaultLoadEventListener.onLoad(DefaultLoadEventListener.java:92) ~[hibernate-core-5.3.7.Final.jar:5.3.7.Final]
    at org.hibernate.internal.SessionImpl.fireLoad(SessionImpl.java:1257) ~[hibernate-core-5.3.7.Final.jar:5.3.7.Final]
    at org.hibernate.internal.SessionImpl.internalLoad(SessionImpl.java:1140) ~[hibernate-core-5.3.7.Final.jar:5.3.7.Final]

我所知道的

我确定问题在于UserUserPermission 之间的“递归”关系。

如果我在UserPermission 中删除到User 的映射,异常就会消失:

public class UserPermission {
    @Id @NonNull @NotNull
    private String user;

我不知道的事

如何映射这两个实体而不出现此异常,实体是否未映射并不重要我只想强制执行关系

更新 1

将 mappedBy 属性添加到 User 实体中的 OneToMany 注释并移除 JoinColumn 注释:

@JsonIgnore
@OneToMany(cascade = CascadeType.ALL, fetch = FetchType.LAZY, mappedBy = "user")
private Collection<UserPermission> permissions;

没有解决问题,但堆栈跟踪发生了变化:

java.lang.StackOverflowError: null
    at java.lang.ThreadLocal.get(ThreadLocal.java:161) ~[na:1.8.0_151]
    at io.micrometer.core.instrument.binder.logging.MetricsTurboFilter.decide(LogbackMetrics.java:132) ~[micrometer-core-1.1.3.jar:1.1.3]
    at ch.qos.logback.classic.spi.TurboFilterList.getTurboFilterChainDecision(TurboFilterList.java:49) ~[logback-classic-1.2.3.jar:na]
    at ch.qos.logback.classic.LoggerContext.getTurboFilterChainDecision_0_3OrMore(LoggerContext.java:269) ~[logback-classic-1.2.3.jar:na]
    at ch.qos.logback.classic.Logger.callTurboFilters(Logger.java:751) ~[logback-classic-1.2.3.jar:na]
    at ch.qos.logback.classic.Logger.isTraceEnabled(Logger.java:623) ~[logback-classic-1.2.3.jar:na]
    at org.apache.logging.slf4j.SLF4JLogger.isEnabledFor(SLF4JLogger.java:213) ~[log4j-to-slf4j-2.11.2.jar:2.11.2]
    at org.apache.logging.slf4j.SLF4JLogger.isEnabled(SLF4JLogger.java:121) ~[log4j-to-slf4j-2.11.2.jar:2.11.2]
    at org.apache.logging.log4j.spi.AbstractLogger.isEnabled(AbstractLogger.java:1504) ~[log4j-api-2.11.2.jar:2.11.2]
    at org.jboss.logging.Log4j2Logger.isEnabled(Log4j2Logger.java:46) ~[jboss-logging-3.3.2.Final.jar:3.3.2.Final]
    at org.jboss.logging.Logger.isTraceEnabled(Logger.java:98) ~[jboss-logging-3.3.2.Final.jar:3.3.2.Final]
    at org.jboss.logging.DelegatingBasicLogger.isTraceEnabled(DelegatingBasicLogger.java:54) ~[jboss-logging-3.3.2.Final.jar:3.3.2.Final]

    // Repeated over and over   

    at org.hibernate.persister.entity.AbstractEntityPersister.load(AbstractEntityPersister.java:4269) ~[hibernate-core-5.3.7.Final.jar:5.3.7.Final]
    at org.hibernate.event.internal.DefaultLoadEventListener.loadFromDatasource(DefaultLoadEventListener.java:511) ~[hibernate-core-5.3.7.Final.jar:5.3.7.Final]
    at org.hibernate.event.internal.DefaultLoadEventListener.doLoad(DefaultLoadEventListener.java:481) ~[hibernate-core-5.3.7.Final.jar:5.3.7.Final]
    at org.hibernate.event.internal.DefaultLoadEventListener.load(DefaultLoadEventListener.java:222) ~[hibernate-core-5.3.7.Final.jar:5.3.7.Final]
    at org.hibernate.event.internal.DefaultLoadEventListener.proxyOrLoad(DefaultLoadEventListener.java:281) ~[hibernate-core-5.3.7.Final.jar:5.3.7.Final]
    at org.hibernate.event.internal.DefaultLoadEventListener.doOnLoad(DefaultLoadEventListener.java:124) ~[hibernate-core-5.3.7.Final.jar:5.3.7.Final]
    at org.hibernate.event.internal.DefaultLoadEventListener.onLoad(DefaultLoadEventListener.java:92) ~[hibernate-core-5.3.7.Final.jar:5.3.7.Final]
    at org.hibernate.internal.SessionImpl.fireLoad(SessionImpl.java:1257) ~[hibernate-core-5.3.7.Final.jar:5.3.7.Final]
    at org.hibernate.internal.SessionImpl.internalLoad(SessionImpl.java:1140) ~[hibernate-core-5.3.7.Final.jar:5.3.7.Final]
    at org.hibernate.type.EntityType.resolveIdentifier(EntityType.java:682) ~[hibernate-core-5.3.7.Final.jar:5.3.7.Final]
    at org.hibernate.type.EntityType.resolve(EntityType.java:464) ~[hibernate-core-5.3.7.Final.jar:5.3.7.Final]
    at org.hibernate.type.ManyToOneType.resolve(ManyToOneType.java:239) ~[hibernate-core-5.3.7.Final.jar:5.3.7.Final]
    at org.hibernate.type.EntityType.resolve(EntityType.java:457) ~[hibernate-core-5.3.7.Final.jar:5.3.7.Final]
    at org.hibernate.type.ComponentType.resolve(ComponentType.java:688) ~[hibernate-core-5.3.7.Final.jar:5.3.7.Final]
    at org.hibernate.loader.Loader.extractKeysFromResultSet(Loader.java:862) ~[hibernate-core-5.3.7.Final.jar:5.3.7.Final]
    at org.hibernate.loader.Loader.getRowFromResultSet(Loader.java:718) ~[hibernate-core-5.3.7.Final.jar:5.3.7.Final]
    at org.hibernate.loader.Loader.processResultSet(Loader.java:990) ~[hibernate-core-5.3.7.Final.jar:5.3.7.Final]
    at org.hibernate.loader.Loader.doQuery(Loader.java:948) ~[hibernate-core-5.3.7.Final.jar:5.3.7.Final]
    at org.hibernate.loader.Loader.doQueryAndInitializeNonLazyCollections(Loader.java:340) ~[hibernate-core-5.3.7.Final.jar:5.3.7.Final]
    at org.hibernate.loader.Loader.doQueryAndInitializeNonLazyCollections(Loader.java:310) ~[hibernate-core-5.3.7.Final.jar:5.3.7.Final]
    at org.hibernate.loader.Loader.loadEntity(Loader.java:2281) ~[hibernate-core-5.3.7.Final.jar:5.3.7.Final]
    at org.hibernate.loader.entity.AbstractEntityLoader.load(AbstractEntityLoader.java:64) ~[hibernate-core-5.3.7.Final.jar:5.3.7.Final]
    at org.hibernate.loader.entity.AbstractEntityLoader.load(AbstractEntityLoader.java:54) ~[hibernate-core-5.3.7.Final.jar:5.3.7.Final]

【问题讨论】:

    标签: java spring hibernate jpa spring-data-jpa


    【解决方案1】:

    解决方案是从父实体(用户)中删除@JoinColumn,并按照piyush-tyagi 的建议使用带有@OneToMany 的mappedBy 属性:

    @Entity
    @JsonIgnoreProperties({ "hibernateLazyInitializer", "handler" })
    @NoArgsConstructor @RequiredArgsConstructor @AllArgsConstructor
    public class User {
        @Id
        @NonNull @NotNull
        private String id;
    
        // ... Other non pk fields
    
        @JsonIgnore
        @OneToMany(cascade = CascadeType.ALL, fetch = FetchType.LAZY, mappedBy = "user")
        private Collection<UserPermission> permissions;
    }
    

    子实体中的pk使用@EmbeddedId(UserPermission):

    @Entity
    @JsonIgnoreProperties({ "hibernateLazyInitializer", "handler" })
    @NoArgsConstructor @AllArgsConstructor @RequiredArgsConstructor
    public class UserPermission {
        @EmbeddedId
        private PK pk;
    
        @Embeddable
        @Getter @Setter @NoArgsConstructor @AllArgsConstructor
        public static class PK implements Serializable {
            private String user;
    
            private String permission;
        }
    }
    

    并使用@MapsId映射父实体

    @MapsId("user")
    @NonNull @NotNull
    @ManyToOne
    @JoinColumn(name = "user", updatable = false, insertable = false)
    private User user;
    
    @MapsId("permission")
    @NonNull @NotNull
    @ManyToOne
    @JoinColumn(name = "permission", updatable = false, insertable = false)
    private Permission permission;
    

    最后,实现 getter/setter,使字段同步:

    @JsonIgnore
    public PK getPk() {
        if (pk == null) {
            pk = new PK();
        }
    
        return pk;
    }
    
    public void setPk(PK pk) {
        this.pk = pk;
        this.user = new User(pk.getUser());
        this.permission = new Permission(pk.getPermission());
    }
    
    public User getUser() {
        if (user == null) {
            user = new User(getPk().getUser());
        }
    
        return user;
    }
    
    public void setUser(User user) {
        this.user = user;
        getPk().setUser(user.getId());
    }
    
    public Permission getPermission() {
        if (permission == null) {
            permission = new Permission(getPk().getPermission());
        }
    
        return permission;
    }
    
    public void setPermission(Permission permission) {
        this.permission = permission;
        getPk().setPermission(permission.getId());
    }
    

    【讨论】:

      【解决方案2】:

      由于您在用户类中具有双向关系,并且具有一对多关系,因此您应该使用 @mappedby 而不是 @joincolumn,我认为这会导致递归过程,从而导致 stackoverflow 错误

      【讨论】:

      • 你的意思是在 User 还是 UserPermission 实体?
      • 在用户实体中,因为您已经在 userpermission 中拥有 joincloumn 也是最佳实践,将多对一实体作为关系所有者,而不是一对多,因此任何时候您遇到这种情况总是在 onetomany 和 @ 上使用 mappedby在 manytoone 上加入列
      • 感谢您的建议。我添加了 mappedBy 并删除了 JoinColumn 但问题仍然存在(我编辑了问题)。
      • 从hibernate查看sql日志,它获取用户权限,权限,然后用户一遍又一遍
      • 这是因为主键中有用户作为字段。
      【解决方案3】:

      我遇到了类似的问题,去掉了实体类中的 lombok 注释并创建了 getter 和 setter,这解决了我的问题。

      【讨论】:

        猜你喜欢
        • 1970-01-01
        • 2015-02-13
        • 2019-02-24
        • 1970-01-01
        • 2011-11-15
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 2019-05-22
        相关资源
        最近更新 更多