简体   繁体   中英

Spring projection with entity inside

I need in metainfo for entity (hierarchy level from recursive sql query) so i created next projection

@Value
public class ProjectionObject{
    MyEntity entity;
    int metainfo;
}

@Query(value = "select my_entity.*, 1 as metainfo from my_entities", nativeQuery = true)
List<ProjectionObject> findSome();

But it returns List<List> but i expect List.

As result i what to manipulate with ProjectionObject#entity as with managed (by Entity Manager) ProjectionObject#entity, in other word i want to get managed entity with metainfo once without getting fe hierarchy Ids and after get entities

I'm not sure Spring Data Projections supports that.

However, this is a perfect use case forBlaze-Persistence Entity Views .

Blaze-Persistence is a query builder on top of JPA which supports many of the advanced DBMS features on top of the JPA model. I created Entity Views on top of it to allow easy mapping between JPA models and custom interface defined models, something like Spring Data Projections on steroids. The idea is that you define your target structure the way you like and map attributes(getters) via JPQL expressions to the entity model. Since the attribute name is used as default mapping, you mostly don't need explicit mappings as 80% of the use cases is to have DTOs that are a subset of the entity model.

A projection with Entity Views could look as simple as the following

@EntityView(MyEntity.class)
interface ProjectionObject {
    @Mapping("this")
    MyEntity getEntity();
    @Mapping("1")
    int getMetaInfo();
}

Querying is a matter of applying the entity view to a query, the simplest being just a query by id.

ProjectionObject dto = entityViewManager.find(entityManager, ProjectionObject.class, id);

But the Spring Data integration allows you to use it almost like Spring Data Projections: https://persistence.blazebit.com/documentation/entity-view/manual/en_US/index.html#spring-data-features

List<ProjectionObject> findAll();

You can also make use of updatable entity views which allows you to eliminate the entity type completely, which reduces the amount of data fetched and flush back only the parts that you actually want to change:

@UpdatableEntityView
@EntityView(MyEntity.class)
interface ProjectionObject {
    @IdMapping
    Integer getId();
    String getName();
    void setName(String name);
    @Mapping("1")
    int getMetaInfo();
}

Now you can fetch that object and then after changing the state flush it back to the database:

ProjectionObject o = repository.findOne(123);
o.setName(o.getName().toUpperCase());
repository.save(o);

And it will only flush back the name as you will see in the SQL.

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