# Upgrading to Hibernate 6, EntityGraph annotation has not the same behaviour as before

**URL:** <https://discourse.hibernate.org/t/upgrading-to-hibernate-6-entitygraph-annotation-has-not-the-same-behaviour-as-before/9098>\
**Category:** Hibernate ORM\
**Created:** [February 26, 2024, 10:26am UTC](https://discourse.hibernate.org/t/upgrading-to-hibernate-6-entitygraph-annotation-has-not-the-same-behaviour-as-before/9098 "2024-02-26T10:26:38Z")\
**Posts on this page:** 5\
**Page:** 1

<div class="post-metadata">

**Author:** ![waiche](https://avatars.discourse-cdn.com/v4/letter/w/439d5e/32.png) [@waiche](https://discourse.hibernate.org/u/waiche)\
**Post date:** [February 26, 2024, 10:26am UTC](https://discourse.hibernate.org/t/upgrading-to-hibernate-6-entitygraph-annotation-has-not-the-same-behaviour-as-before/9098/1 "2024-02-26T10:26:38Z")

</div>

Hello everyone,

Recently I upgraded my project from Sprint Boot 2.5.14 to 3.1.5  
By the way Hibernate to 5.4.33 to 6.2.13

This request works fine before upgrading, it seems that @entitygraph is not working as before

Repository

```auto
@EntityGraph(attributePaths = { "releaseFeatures" })
  @Query(
    "SELECT release FROM Release release LEFT JOIN release.releaseFeatures rf " +
    "WHERE rf.isDeleted IS FALSE AND ((release.id = 1 and release.isPublished = true) OR (release.id = 2))"
  )
  List<Release> findActive();

```

Entities

````auto
@Entity
@Table(name = "releases")
public class Release implements Serializable {

  @Id
  @GeneratedValue(strategy = GenerationType.IDENTITY)
  private Long id;

  @Enumerated(EnumType.STRING)
  private ReleaseVersionEnum version;

  @JsonDeserialize(converter = DateRFC1123ToZonedDateTimeConverter.class)
  private ZonedDateTime dateToPublish;

  @JsonDeserialize(converter = DateRFC1123ToZonedDateTimeConverter.class)
  private ZonedDateTime dateOfDeployment;

    private boolean isPublished;

  @OneToMany(mappedBy = "release", cascade = CascadeType.ALL, orphanRemoval = true)
  private Set<ReleaseFeature> releaseFeatures = new HashSet<>();```

...
}

````

```auto
@Entity
@Table(name = "release_features")
public class ReleaseFeature implements Serializable {

  @JsonIgnore
  @Id
  @GeneratedValue(strategy = GenerationType.IDENTITY)
  private Long id;

  @NaturalId
  @Column(name = "uuid", unique = true)
  private String uuid;

  @JsonIgnore
  @ManyToOne(fetch = FetchType.LAZY)
  @JsonIgnoreProperties(value = { "applications", "hibernateLazyInitializer" })
  @JoinColumn(name = "release_id", nullable = false)
  private Release release;
....
}

```

Table Release

| id | version | date\_to\_publish | date\_of\_deployment | is\_published |
| --- | --- | --- | --- | --- |
| 1 | CURRENT | 2024-02-23 00:00:00.000 | 2024-02-23 00:00:00.000 | true |
| 2 | NEXT | null | null | false |

Table Release\_features

| id | uuid | release\_id | title\_translation\_code | description\_translation\_code | is\_deleted | deleted\_date |
| --- | --- | --- | --- | --- | --- | --- |
| 44 | uuid-1 | 1 | RELEASE\_CONTENT\_TITLE\_01\_FR | RELEASE\_CONTENT\_DESC\_01\_FR | true | 2022-04-12 09:46:36.260 |
| 45 | uuid-2 | 1 | RELEASE\_CONTENT\_TITLE\_02\_FR | RELEASE\_CONTENT\_DESC\_02\_FR | true | 2022-04-12 09:46:36.260 |
| 46 | uuid-2 | 1 | RELEASE\_CONTENT\_TITLE\_03\_FR | RELEASE\_CONTENT\_DESC\_03\_FR | true | 2022-04-12 09:46:36.260 |
| 47 | uuid-2 | 1 | RELEASE\_CONTENT\_TITLE\_04\_FR | RELEASE\_CONTENT\_DESC\_04\_FR | false | 2022-04-12 09:46:36.260 |

Hibernate debug  
version 5.4.33

```auto
select
    release0_.id as id1_37_0_,
    releasefea1_.id as id1_36_1_,
    release0_.date_of_deployment as date_of_2_37_0_,
    release0_.date_to_publish as date_to_3_37_0_,
    release0_.is_published as is_publi4_37_0_,
    release0_.version as version5_37_0_,
    releasefea1_.deleted_date as deleted_2_36_1_,
    releasefea1_.description_translation_code as descript3_36_1_,
    releasefea1_.is_deleted as is_delet4_36_1_,
    releasefea1_.release_id as release_7_36_1_,
    releasefea1_.title_translation_code as title_tr5_36_1_,
    releasefea1_.uuid as uuid6_36_1_,
    releasefea1_.release_id as release_7_36_0__,
    releasefea1_.id as id1_36_0__
from
    releases release0_
        left outer join
    release_features releasefea1_
    on release0_.id=releasefea1_.release_id
where
    releasefea1_.is_deleted=0
  and (
    release0_.id=1
        and release0_.is_published=1
        or release0_.id=2
    )

```

Version 6.2.13

```auto
select
    r1_0.id,
    r1_0.date_of_deployment,
    r1_0.date_to_publish,
    r1_0.is_published,
    r1_0.version
from
    releases r1_0
        left join
    release_features r2_0
    on r1_0.id=r2_0.release_id
where
    r2_0.is_deleted=0
  and (
    (
        r1_0.id=1
            and r1_0.is_published=1
        )
        or (
        r1_0.id=2
        )
    )

select
    r1_0.release_id,
    r1_0.id,
    r1_0.deleted_date,
    r1_0.description_translation_code,
    r1_0.is_deleted,
    r1_0.title_translation_code,
    r1_0.uuid
from
    release_features r1_0
where
    r1_0.release_id=1;

```

With 6.2.13, I had this Trace:  
`JdbcValuesSourceProcessingStateStandardImpl: Skipping create subselects because there are fewer than 2 results, so query by key is more efficient.`

Instead of returning the only line from `release_features` ( is\_deleted = false ), it returns all lines

Is it possible to have the same behaviour as before ? May be I miss some configurations ?

---

<div class="post-metadata">

**Author:** ![beikov](https://yyz1.discourse-cdn.com/flex035/user_avatar/discourse.hibernate.org/beikov/32/258_2.png) [@beikov](https://discourse.hibernate.org/u/beikov)\
**Post date:** [February 26, 2024, 2:41pm UTC](https://discourse.hibernate.org/t/upgrading-to-hibernate-6-entitygraph-annotation-has-not-the-same-behaviour-as-before/9098/2 "2024-02-26T14:41:34Z")

</div>

The result you are receiving now is correct and ORM 5 had a bug. If you want to filter collections, use [Hibernate filters](https://docs.jboss.org/hibernate/orm/6.4/userguide/html_single/Hibernate_User_Guide.html#pc-filtering) or the [`@Where` annotation](https://docs.jboss.org/hibernate/orm/6.4/javadocs/org/hibernate/annotations/Where.html). Alternatively, you can also make use of the [new soft delete feature of ORM 6.4](https://docs.jboss.org/hibernate/orm/6.4/userguide/html_single/Hibernate_User_Guide.html#soft-delete).

---

<div class="post-metadata">

**Author:** ![waiche](https://avatars.discourse-cdn.com/v4/letter/w/439d5e/32.png) [@waiche](https://discourse.hibernate.org/u/waiche)\
**Post date:** [February 26, 2024, 3:56pm UTC](https://discourse.hibernate.org/t/upgrading-to-hibernate-6-entitygraph-annotation-has-not-the-same-behaviour-as-before/9098/3 "2024-02-26T15:56:15Z")

</div>

Thanks for your feedback  
Finally, I removed EntityGraph annotation and used LEFT JOIN FETCH

```auto
@Query(
    "SELECT release FROM Release release LEFT JOIN FETCH release.releaseFeatures rf " +
    "WHERE rf.isDeleted = FALSE AND ((release.id = 1 and release.isPublished = true) OR (release.id = 2))"
  )
  List<Release> findActive();

```

---

<div class="post-metadata">

**Author:** ![beikov](https://yyz1.discourse-cdn.com/flex035/user_avatar/discourse.hibernate.org/beikov/32/258_2.png) [@beikov](https://discourse.hibernate.org/u/beikov)\
**Post date:** [February 26, 2024, 4:14pm UTC](https://discourse.hibernate.org/t/upgrading-to-hibernate-6-entitygraph-annotation-has-not-the-same-behaviour-as-before/9098/4 "2024-02-26T16:14:40Z")

</div>

Doing that comes with the risk that Hibernate ORM might remove data that you filtered out if the collection is changed. I strongly recommend you to use one of the supported variants that I suggested.

---

<div class="post-metadata">

**Author:** ![waiche](https://avatars.discourse-cdn.com/v4/letter/w/439d5e/32.png) [@waiche](https://discourse.hibernate.org/u/waiche)\
**Post date:** [February 27, 2024, 9:01am UTC](https://discourse.hibernate.org/t/upgrading-to-hibernate-6-entitygraph-annotation-has-not-the-same-behaviour-as-before/9098/5 "2024-02-27T09:01:25Z")

</div>

Thank you for your help, finally I applied your recommendations

```auto
@Entity
@Table(name = "releases")
public class Release implements Serializable {

....
  @OneToMany(mappedBy = "release", cascade = CascadeType.ALL, orphanRemoval = true)
  @Fetch(FetchMode.JOIN)
  @Where(clause = "is_deleted = 0")
  private Set<ReleaseFeature> releaseFeatures = new HashSet<>();
....
}

```

```auto
@Repository
public interface ReleaseRepository extends JpaRepository<Release, Long> {
  @Query(
    "SELECT release FROM Release release " +
    "WHERE ((release.id = 1 and release.isPublished = true) OR (release.id = 2))"
  )
  List<Release> findActive();
}

```
