Interface StatelessSession

All Superinterfaces:
AutoCloseable, EntityAgent, EntityHandler, Serializable, SharedSessionContract
All Known Subinterfaces:
StatelessSessionImplementor

public interface StatelessSession extends SharedSessionContract, EntityAgent
A command-oriented API often used for performing bulk operations against the database. A stateless session has no persistence context, and always works directly with detached entity instances. When a method of this interface is called, any necessary interaction with the database happens immediately and synchronously.

Viewed in opposition to Session, the StatelessSession is a whole competing programming model, one preferred by some developers for its simplicity and somewhat lower level of abstraction. But the two kinds of session are not enemies, and may comfortably coexist in a single program.

A stateless session comes some with designed-in limitations:

  • it does not have a first-level cache,
  • nor does it implement transactional write-behind or automatic dirty checking.

Furthermore, the basic operations of a stateless session do not have corresponding cascade types, and so an operation performed on one entity via a stateless session never cascades to associated entities.

The basic operations of a stateless session are EntityHandler.get(Class, Object), insert(Object), update(Object), delete(Object), and upsert(Object). These operations are always performed synchronously, resulting in immediate access to the database. Notice that update is an explicit operation. There is no "flush" operation for a stateless session, and so modifications to entities are never automatically detected and made persistent.

Similarly, lazy association fetching is an explicit operation. A collection or proxy may be fetched by calling fetch(Object).

Stateless sessions are vulnerable to data aliasing effects, due to the lack of a first-level cache.

On the other hand, for certain kinds of transactions, a stateless session may perform slightly faster than a stateful session.

Certain rules applying to stateful sessions are relaxed in a stateless session:

  • it's not necessary to discard a stateless session and its entities after an exception is thrown by the stateless session, and
  • when an exception is thrown by a stateless session, the current transaction is not automatically marked for rollback.

Since version 7, the configuration property "hibernate.jdbc.batch_size" has no effect on a stateless session. Automatic batching may be enabled by explicitly setting the batch size. However, automatic batching has the side effect of delaying execution of the batched operation, thus undermining the synchronous nature of operations performed through a stateless session. A preferred approach is to explicitly batch operations via insertMultiple(List), updateMultiple(List), or deleteMultiple(List).

Since version 7, a stateless session makes use of the second-level cache by default. To bypass the second-level cache, call SharedSessionContract.setCacheMode(CacheMode), passing CacheMode.IGNORE, or set the configuration properties "jakarta.persistence.cache.retrieveMode" and "jakarta.persistence.cache.storeMode" to BYPASS.

  • Method Details

    • insert

      void insert(@Nonnull Object entity)
      Insert a record.

      If the entity @Id field is declared to be generated, for example, if it is annotated @GeneratedValue, the id is generated and assigned to the given instance.

      The PostPersist callback will be triggered if the operation is successful.

      Specified by:
      insert in interface EntityAgent
      Parameters:
      entity - a new transient instance
    • insertMultiple

      void insertMultiple(@Nonnull List<?> entities)
      Insert multiple records in the same order as the entity instances representing the new records occur in the given list.
      Specified by:
      insertMultiple in interface EntityAgent
      Parameters:
      entities - a list of transient instances to be inserted
      Since:
      7.0
    • insert

      Object insert(@Nonnull String entityName, @Nonnull Object entity)
      Insert a record.

      The PostPersist callback will be triggered if the operation is successful.

      Parameters:
      entityName - The entityName for the entity to be inserted
      entity - a new transient instance
      Returns:
      the identifier of the instance
    • update

      void update(@Nonnull Object entity)
      Update a record.

      The PostUpdate callback will be triggered if the operation is successful.

      Specified by:
      update in interface EntityAgent
      Parameters:
      entity - a detached entity instance
    • updateMultiple

      void updateMultiple(@Nonnull List<?> entities)
      Update multiple records in the same order as the entity instances representing the records occur in the given list.
      Specified by:
      updateMultiple in interface EntityAgent
      Parameters:
      entities - a list of detached instances to be updated
      Since:
      7.0
    • update

      void update(@Nonnull String entityName, @Nonnull Object entity)
      Update a record.

      The PostUpdate callback will be triggered if the operation is successful.

      Parameters:
      entityName - The entityName for the entity to be updated
      entity - a detached entity instance
    • delete

      void delete(@Nonnull Object entity)
      Delete a record.

      The PostRemove callback will be triggered if the operation is successful.

      Specified by:
      delete in interface EntityAgent
      Parameters:
      entity - a detached entity instance
    • deleteMultiple

      void deleteMultiple(@Nonnull List<?> entities)
      Delete multiple records in the same order as the entity instances representing the records occur in the given list.
      Specified by:
      deleteMultiple in interface EntityAgent
      Parameters:
      entities - a list of detached instances to be deleted
      Since:
      7.0
    • delete

      void delete(@Nonnull String entityName, @Nonnull Object entity)
      Delete a record.

      The PostRemove callback will be triggered if the operation is successful.

      Parameters:
      entityName - The entity name for the entity to be deleted
      entity - a detached entity instance
    • upsert

      void upsert(@Nonnull Object entity)
      Use a SQL merge into statement to perform an upsert, that is, to insert the record if it does not exist, or update it if it already exists.

      This method never performs id generation, and does not accept an entity instance with a null identifier. When id generation is required, use insert(Object).

      On the other hand, upsert() does accept an entity instance with an assigned identifier value, even if the entity @Id field is declared to be generated, for example, if it is annotated @GeneratedValue. Thus, this method may be used to import data from an external source.

      Specified by:
      upsert in interface EntityAgent
      Parameters:
      entity - a detached entity instance, or a new instance with an assigned identifier
      Throws:
      TransientObjectException - if the entity has a null id
      Since:
      6.3
    • upsertMultiple

      void upsertMultiple(@Nonnull List<?> entities)
      Upsert multiple records, that is, for a given record, insert the record if it does not exist or update the record if it already exists, in the same order as the entity instances representing the records occur in the given list.
      Specified by:
      upsertMultiple in interface EntityAgent
      Parameters:
      entities - a list of detached instances and new instances with assigned identifiers
      Since:
      7.0
    • upsert

      void upsert(@Nonnull String entityName, @Nonnull Object entity)
      Use a SQL merge into statement to perform an upsert.
      Parameters:
      entityName - The entity name for the entity to be merged
      entity - a detached entity instance
      Throws:
      TransientObjectException - if the entity has a null id
      Since:
      6.3
    • get

      @Nonnull @Deprecated(forRemoval=true, since="8.0") Object get(@Nonnull String entityName, @Nonnull Object id, @Nonnull LockMode lockMode)
      Deprecated, for removal: This API element is subject to removal in a future version.
      Retrieve a record, obtaining the specified lock mode.
      Parameters:
      entityName - The name of the entity to retrieve
      id - The id of the entity to retrieve
      lockMode - The lock mode to apply to the entity
      Returns:
      a detached entity instance, or null if there is no instance with the given id
    • get

      @Nonnull @Deprecated(forRemoval=true, since="8.0") <T> T get(@Nonnull EntityGraph<T> graph, @Nonnull GraphSemantic graphSemantic, @Nonnull Object id)
      Deprecated, for removal: This API element is subject to removal in a future version.
      Retrieve a record, fetching associations specified by the given EntityGraph.
      Parameters:
      graph - The EntityGraph
      graphSemantic - a GraphSemantic specifying how the graph should be interpreted
      id - The id of the entity to retrieve
      Returns:
      a detached entity instance, or null if there is no instance with the given id
      Since:
      6.3
    • get

      @Nonnull @Deprecated(forRemoval=true, since="8.0") <T> T get(@Nonnull EntityGraph<T> graph, @Nonnull GraphSemantic graphSemantic, @Nonnull Object id, @Nonnull LockMode lockMode)
      Deprecated, for removal: This API element is subject to removal in a future version.
      Retrieve a record, fetching associations specified by the given EntityGraph, and obtaining the specified lock mode.
      Parameters:
      graph - The EntityGraph
      graphSemantic - a GraphSemantic specifying how the graph should be interpreted
      id - The id of the entity to retrieve
      lockMode - The lock mode to apply to the entity
      Returns:
      a detached entity instance, or null if there is no instance with the given id
      Since:
      6.3
    • getMultiple

      @Nonnull @Deprecated(forRemoval=true, since="8.0") <T> List<T> getMultiple(@Nonnull EntityGraph<T> entityGraph, @Nonnull GraphSemantic graphSemantic, @Nonnull List<?> ids)
      Deprecated, for removal: This API element is subject to removal in a future version.
      Retrieve multiple rows, returning instances of the root entity of the given EntityGraph with the fetched associations specified by the graph, in a list where the position of an instance in the list matches the position of its identifier in the given array, and the list contains a null value if there is no persistent instance matching a given identifier.
      Parameters:
      entityGraph - The EntityGraph
      graphSemantic - a GraphSemantic specifying how the graph should be interpreted
      ids - The ids of the entities to retrieve
      Returns:
      an ordered list of detached entity instances, with null elements representing missing entities
      Since:
      7.0
    • refresh

      void refresh(@Nonnull Object entity)
      Refresh the entity instance state from the database.
      Specified by:
      refresh in interface EntityAgent
      Parameters:
      entity - The entity to be refreshed.
    • refresh

      void refresh(@Nonnull String entityName, @Nonnull Object entity)
      Refresh the entity instance state from the database.
      Parameters:
      entityName - The entity name for the entity to be refreshed.
      entity - The entity to be refreshed.
    • refresh

      void refresh(@Nonnull Object entity, @Nonnull LockMode lockMode)
      Refresh the entity instance state from the database.
      Parameters:
      entity - The entity to be refreshed.
      lockMode - The LockMode to be applied.
    • refresh

      void refresh(@Nonnull String entityName, @Nonnull Object entity, @Nonnull LockMode lockMode)
      Refresh the entity instance state from the database.
      Parameters:
      entityName - The entity name for the entity to be refreshed.
      entity - The entity to be refreshed.
      lockMode - The LockMode to be applied.
    • fetch

      @Nonnull <T> T fetch(@Nonnull T association)
      Fetch an association or collection that's configured for lazy loading.
      Book book = session.get(Book.class, isbn);  // book is immediately detached
      session.fetch(book.getAuthors());           // fetch the associated authors
      book.getAuthors().forEach(author -> ... );  // iterate the collection
      

      Warning: this operation in a stateless session is quite sensitive to data aliasing effects and should be used with great care. It's usually better to fetch associations using eager join fetching.

      Specified by:
      fetch in interface EntityAgent
      Parameters:
      association - a lazy-loaded association
      Since:
      6.0
      See Also:
    • getIdentifier

      @Nullable Object getIdentifier(@Nonnull Object entity)
      Return the identifier value of the given entity, which may be detached.
      Parameters:
      entity - a persistent instance associated with this session
      Returns:
      the identifier
      Since:
      6.6