|
| 1 | += What's New in 7.0 |
| 2 | +:toc: |
| 3 | +:toclevels: 4 |
| 4 | +:docsBase: https://docs.jboss.org/hibernate/orm |
| 5 | +:versionDocBase: {docsBase}/7.0 |
| 6 | +:userGuideBase: {versionDocBase}/userguide/html_single/Hibernate_User_Guide.html |
| 7 | +:migrationGuide: {versionDocBase}/migration-guide/migration-guide.html |
| 8 | + |
| 9 | +Describes the new features and capabilities added to Hibernate ORM in 7.0. |
| 10 | + |
| 11 | +If migrating from 6.6, be sure to also check out the link:{migrationGuide}[Migration Guide] for discussion of impactful changes. |
| 12 | + |
| 13 | +[[relicense]] |
| 14 | +== Apache License |
| 15 | + |
| 16 | +Starting with 7.0, Hibernate ORM will be licensed under the Apache License 2.0. |
| 17 | + |
| 18 | +Details can be seen at https://hibernate.atlassian.net/browse/HHH-19145. |
| 19 | + |
| 20 | +As part of this effort, the Hibernate team reached out to the authors of |
| 21 | +"non-trivial" contributions to request permission to relicense their |
| 22 | +work under the Apache License. The response was overwhelming positive, although |
| 23 | +we never heard back from some contributors and another explicitly disagreed. |
| 24 | +This required a few actions on our part: |
| 25 | + |
| 26 | +* Dropping `hibernate-ucp` - see https://hibernate.atlassian.net/browse/HHH-19162 |
| 27 | +* Dropping `TeradataDialect` - see https://hibernate.atlassian.net/browse/HHH-19057 |
| 28 | + |
| 29 | +[[java-17]] |
| 30 | +== Java 17 |
| 31 | + |
| 32 | +Java 17 is the new baseline Java version. |
| 33 | + |
| 34 | + |
| 35 | +[[jpa-32]] |
| 36 | +== Jakarta Persistence 3.2 |
| 37 | + |
| 38 | +7.0 migrates to Jakarta Persistence 3.2, which is fairly disruptive. |
| 39 | +See this https://in.relation.to/2024/04/01/jakarta-persistence-3/[blog post] for a good discussion of the changes. |
| 40 | + |
| 41 | +- https://ci.hibernate.org/view/ORM/job/hibernate-orm-tck-3.2/job/wip%252F7.0/24/[TCK Results] with Java 17 |
| 42 | +- https://ci.hibernate.org/view/ORM/job/hibernate-orm-tck-3.2/job/wip%252F7.0/25/[TCK Results] with Java 21 |
| 43 | + |
| 44 | + |
| 45 | +[[hibernate-models]] |
| 46 | +== Hibernate Models |
| 47 | + |
| 48 | +For many years Hibernate has used the Hibernate Commons Annotations (HCANN) library for handling various low-level tasks |
| 49 | +related to understanding the structure of an application domain model, reading annotations and weaving in XML |
| 50 | +mapping documents. |
| 51 | +The https://github.com/hibernate/hibernate-models[Hibernate Models] project was developed to be a better alternative |
| 52 | +to HCANN. |
| 53 | +7.0 uses Hibernate Models in place of HCANN. |
| 54 | + |
| 55 | + |
| 56 | +[[soft-delete-timestamp]] |
| 57 | +== @SoftDelete with TIMESTAMP |
| 58 | + |
| 59 | +Soft-delete now supports the strategy of tracking the timestamp at which the soft-delete occurred, |
| 60 | +in addition to the previous truth-based strategies. |
| 61 | +See the link:{userGuideBase}#soft-delete[User Guide] for details. |
| 62 | + |
| 63 | +[[embedded-column-naming]] |
| 64 | +== @EmbeddedColumnNaming |
| 65 | + |
| 66 | +A long-requested feature for both Hibernate and Jakarta Persistence has been the ability to |
| 67 | +define a prefix for the names of columns associated with an embedded value. |
| 68 | + |
| 69 | +7.0 adds support for this using the new `@EmbeddedColumnNaming` annotation. The annotation |
| 70 | +accepts a format pattern, so is more flexible than just a prefix. |
| 71 | + |
| 72 | +[source,java] |
| 73 | +---- |
| 74 | +@Embeddable |
| 75 | +class Address { |
| 76 | + String street; |
| 77 | + String city; |
| 78 | + ... |
| 79 | +} |
| 80 | +
|
| 81 | +@Entity |
| 82 | +class Person { |
| 83 | + ... |
| 84 | + @Embedded |
| 85 | + @EmbeddedColumnNaming("home_%") |
| 86 | + Address homeAddress; |
| 87 | +
|
| 88 | + @Embedded |
| 89 | + @EmbeddedColumnNaming("work_%") |
| 90 | + Address workAddress; |
| 91 | +} |
| 92 | +---- |
| 93 | + |
| 94 | +See the link:{userGuideBase}#embeddable-column-naming[User Guide] for details. |
| 95 | + |
| 96 | + |
| 97 | +[[NamedEntityGraph]] |
| 98 | +== @NamedEntityGraph |
| 99 | + |
| 100 | +A new annotation (`@org.hibernate.annotations.NamedEntityGraph`) has been added to allow |
| 101 | +specifying a named entity-graph using Hibernate's ability to parse a string representation of the graph. |
| 102 | + |
| 103 | + |
| 104 | +[source,java] |
| 105 | +---- |
| 106 | +@Entity |
| 107 | +@NamedEntityGraph( graph="title, isbn, author(name, phoneNumber)" ) |
| 108 | +class Book { |
| 109 | + // ... |
| 110 | +} |
| 111 | +---- |
| 112 | + |
| 113 | + |
| 114 | +See `org.hibernate.graph.GraphParser` for details on the syntax and the |
| 115 | +link:{userGuideBase}#fetching-strategies-dynamic-fetching-entity-graph-parsing-annotation[User Guide] for additional details. |
| 116 | + |
| 117 | + |
| 118 | +[[session-find-multiple]] |
| 119 | +== findMultiple() |
| 120 | + |
| 121 | +The new operation `Session.findMultiple()` provides a convenient way to fetch a batch of entities by id. |
| 122 | +Combined with the `BatchSize` option, allows breaking up the JDBC calls into "batches". |
| 123 | + |
| 124 | + |
| 125 | +[[session-managed-entities]] |
| 126 | +== Direct access to first-level cache |
| 127 | + |
| 128 | +The new operation `Session.getManagedEntities()` allows the application to iterate over all entities in the first-level cache, or over all entities of a given type. |
| 129 | + |
| 130 | + |
| 131 | +[[enum-checks]] |
| 132 | +== Converted Enums and Check Constraints |
| 133 | + |
| 134 | +Hibernate previously added support for generating check constraints for enums mapped using `@Enumerated` |
| 135 | +as part of schema generation. 7.0 adds the same capability for enums mapped using an `AttributeConverter`, |
| 136 | +by asking the converter to convert all the enum constants on start up. |
| 137 | + |
| 138 | + |
| 139 | +[[json-xml-functions]] |
| 140 | +== JSON and XML functions |
| 141 | + |
| 142 | +Support for most of the JSON and XML functions that the SQL standard specifies was added to HQL/Criteria. |
| 143 | +The implementations retain the SQL standard semantics and will throw an error if emulation on a database is impossible. |
| 144 | + |
| 145 | +New functions include: |
| 146 | + |
| 147 | +* construction functions like `json_array()`, `json_object()`, `xmlelement()` and `xmlforest()` |
| 148 | +* query functions like `json_value()`, `json_query()` and `xmlquery()` |
| 149 | +* aggregation functions like `json_agg()`, `json_object_agg()` and `xmlagg()` |
| 150 | +* manipulation functions like `json_set()`, `json_mergepatch()` |
| 151 | +* many others |
| 152 | + |
| 153 | + |
| 154 | +[[set-returning-functions]] |
| 155 | +== Set-returning Functions |
| 156 | + |
| 157 | +A set-returning function is a new type of function that can return rows and is exclusive to the `from` clause. |
| 158 | +The concept is known in many different database SQL dialects and is sometimes referred to as table valued function or table function. |
| 159 | + |
| 160 | +Custom set-returning functions can be registered via a `FunctionContributor`. |
| 161 | +Out-of-the-box, some common set-returning functions are already supported or emulated |
| 162 | + |
| 163 | +* `unnest()` - allows to turn an array into rows |
| 164 | +* `generate_series()` - can be used to create a series of values as rows |
| 165 | +* `json_table()` - turns a JSON document into rows |
| 166 | +* `xmltable()` - turns an XML document into rows |
| 167 | + |
| 168 | + |
| 169 | +[[any-discriminator]] |
| 170 | +== @AnyDiscriminatorImplicitValues |
| 171 | + |
| 172 | +The new `@AnyDiscriminatorImplicitValues` offers 2 related improvements for the mapping of discriminator values |
| 173 | +for `@Any` and `ManyToAny` associations. |
| 174 | + |
| 175 | +First, it allows control over how Hibernate determines the discriminator value to store in the database for |
| 176 | +implicit discriminator mappings. Historically, Hibernate would always use the full name of the associated |
| 177 | +entity. |
| 178 | + |
| 179 | +Second, it allows mixing of explicit and implicit value strategies. |
| 180 | + |
| 181 | +See the link:{userGuideBase}#associations-any[User Guide] for details. |
| 182 | + |
| 183 | + |
| 184 | +[[stateless-session-multiple]] |
| 185 | +== StatelessSession and Batch Operations |
| 186 | + |
| 187 | +`StatelessSession` now supports explicit batch operations via `insertMultiple()`, `updateMultiple()`, or `deleteMultiple()`. |
| 188 | + |
| 189 | + |
| 190 | +[[stateless-session-cache]] |
| 191 | +== StatelessSession and Second Level Cache |
| 192 | + |
| 193 | +Previously, stateless sessions never interacted with the second-level cache. |
| 194 | +This reflected their original intended role in bulk processing. |
| 195 | +With the advent of Jakarta Data and Hibernate Data Repositories, the responsibilities of `StatelessSession` have now expanded, and this behavior is no longer appropriate. |
| 196 | +Thus, a stateless session now makes use of the second-level cache by default. |
| 197 | + |
| 198 | +See the link:{migrationGuide}#stateless-session-cache[Migration Guide] for additional details. |
| 199 | + |
| 200 | + |
| 201 | + |
| 202 | +[[stateless-session-jdbc-batching]] |
| 203 | +== StatelessSession and JDBC Batching |
| 204 | + |
| 205 | +Automatic JDBC batching has the side effect of delaying the execution of the batched operation, and this undermines the synchronous nature of operations performed through a stateless session. |
| 206 | +In Hibernate 7, the configuration property `hibernate.jdbc.batch_size` now has no effect on a stateless session. |
| 207 | +Automatic batching may be enabled by explicitly calling `setJdbcBatchSize()`. |
| 208 | +However, the preferred approach is to <<stateless-session-multiple,explicitly batch operations>> via `insertMultiple()`, `updateMultiple()`, or `deleteMultiple()`. |
| 209 | + |
| 210 | + |
| 211 | +[[transaction-api]] |
| 212 | +== Improvements to Transaction |
| 213 | + |
| 214 | +The `Transaction` interface leaks the SPI type `TransactionStatus` via `getStatus()`, and the JTA-defined type `Synchronization` via `registerSynchronization()`, which breaks layering in a fairly harmless way. |
| 215 | +New operations were added to the `Transaction` interface, allowing code to inspect the status of the transaction or register callbacks without the use of layer-breaking operations. |
| 216 | + |
| 217 | + |
| 218 | +[[schema-manager-populate]] |
| 219 | +== Data population |
| 220 | + |
| 221 | +Setting `jakarta.persistence.schema-generation.database.action=populate` or calling `SchemaManager.populate()` populates an existing schema with initial data in `/import.sql` or other SQL scripts specified via `jakarta.persistence.sql-load-script-source`. |
| 222 | + |
| 223 | + |
| 224 | +[[xml-mapping]] |
| 225 | +== XML mappings |
| 226 | + |
| 227 | +Hibernate's legacy `hbm.xml` mapping schema has been deprecated for quite some time, replaced by a new `mapping.xml` |
| 228 | +schema, which is now stabilized and should be prefered. |
| 229 | +Support for `hbm.xml` mappings will be removed in 8.0. |
| 230 | + |
| 231 | +We offer a transformation of `hbm.xml` files into `mapping.xml` files, which is available both at build-time (Gradle plugin) and at run-time (using `hibernate.transform_hbm_xml.enabled=true`). |
| 232 | + |
0 commit comments