I am using JPA with derby database. I want to retrieve two different result sets from the same table onto two entirely different screens.
Screen one displays values using "ScannerReport" bean.
Screen two will display values from ScannerSummaryReport bean.
Both beans needs to have data from same Entity "Scanner" as mentioned in code below.
How to define that result set mapping onto the entity for two different result sets, having different columns in it
A ---> Query query = em.createNativeQuery(<query for scanner report goes here >,"ScannerReport");
query.getResultList();
Now A will execute and instantiate an object of ScannerReport class , fill it up with data .
B ---> Query query = em.createNativeQuery(<query for scanner summary report goes here>,"ScannerSummaryReport");
query.getResultList();
I want somehow to let JPA know that when i execute B, now it needs to instantiate an object of a different class lets say ScannerSummaryReport fill it up with data from A DIFFERENT QUERY ( written to calcuate averages and totals ) and return the result.Again please not both queries will be from same entity Scanner..
#SqlResultSetMapping(
name="ScannerReport",
classes={
#ConstructorResult(
targetClass=com.beans.ScannerReport.class,
columns={
#ColumnResult(name="scanYear", type=Integer.class),
#ColumnResult(name="julianDay", type=Integer.class),
#ColumnResult(name="scannerId", type=String.class),
#ColumnResult(name="startTime", type=Long.class),
#ColumnResult(name="endTime", type=Long.class),
#ColumnResult(name="scanTime", type=Long.class),
}
)
}
)
#Entity
public class Scanner {
// Class implementation goes here
}
So just define two SqlResultSetMappings, using the #SqlResultSetMappings annotation, one for each query. See http://www.datanucleus.org/products/accessplatform_4_0/jpa/annotations.html#SqlResultSetMappings for an example
Related
I'm trying to join multiple datasources in a grid I created.
The grid is in CaseDetail form and it uses same tables as some other groups on it.
Therefore I have to use joins based on datasources names and not on tables names.
There is InventTable(InventTableComplaints) - parent and EcoResProductTranslation(EcoResProductTranslationComplaints) - child.
What I'm trying to do is to add this code to the child datasource:
public void executeQuery()
{
QueryBuildDataSource qbdsIT, qbdsERPTC;
qbdsIT = InventTableComplaint_DS.queryBuildDataSource();
qbdsERPTC = qbdsIT.addDataSource(tableNum(EcoResProductTranslation), "EcoResProductTranslationComplaint");
qbdsERPTC.addLink(fieldNum(InventTable, Product), fieldNum(EcoResProductTranslation, Product));
qbdsERPTC.joinMode( JoinMode::OuterJoin );
qbdsERPTC.fetchMode( QueryFetchMode::One2One );
super();
}
But it doesn't work.
Is it possible?
You do not define the table relations in the executeQuery method, do so in the init method instead which is executed exactly once. If you defined the datasource in the form (using InventTableComplaint as JoinSource and with OuterJoin as JoinMode), you do not need to do it in init method either, but you may need to define the link if not provided as table relations:
public void init()
{
qbdsIT = InventTableComplaint_DS.queryBuildDataSource();
qbdsERPTC = EcoResProductTranslationComplaint_ds.queryBuildDataSource();
qbdsERPTC.clearLinks();
qbdsERPTC.addLink(fieldNum(InventTable, Product), fieldNum(EcoResProductTranslation, Product));
super();
}
Beware that more than one record of may exist of EcoResProductTranslation for each InventTable (on for each language), so you may end out with "duplicates" of InventTable in the grid.
I want to create a list of complex DTO objects with data from several Entities and one non-Entity-parameter. Let's say my DTO class has constructor:
public MyDto(String entityField, String someString) {...}
and I would like to use the CriteriaBuilder.construct method to create my list by doing like this:
CriteriaBuilder builder = em.getCriteriaBuilder();
CriteriaQuery<MyDto> query = builder.createQuery(MyDto.class);
Root<MyEntity> root = query.from(MyEntity.class);
builder.construct(MyDto.class, root.get("entityField"), someString);
...
but I am not allowed to do it, because the construct method wants from me only javax.persistence.criteria.Selection arguments.
The question: is there is a way to do it similar to this (at one blow) with Criteria API? Or I need to load MyEntity objects first and go through them and create a list of DTOs (not so pretty)?
I use this approach each time I've a projection that collect fields from different entities or for privacy reason i must not return some data (for example passwords)
query.select(
builder.construct(
MyDto.class,
root.get("myfield"), // for field
cb.literal(1), // for number
cb.literal("blah blah") // for string
));
Coming from a Entity Framework Background I can cast my ORM results to a class that contains a subset of the full back-end model's data.
I have a JAX-RS REST Service where I am usually returning something like
MyEntity result = em.createQuery(select e from MyEntity e ... blah blah blah).
I know I can do this:
Object result = em.createQuery(select e.Title, e.Version, e.Date from MyEntity e... blah blah blah).
But can I either a:
Cast my result to a separate class or B name my fields in my createquery such that they are named when returning my JSON?
For example in .Net Land I could do something like....
(select new {Title = e.Title, Version = e.Version})
and then cast this to another type. I tried using a typedquery and casting but I get a "Type X is incompatible with return type Y" type error.
My goal is to return a specific subset (view model/ DTO)of my information for consumption in a specific scenario.
E.g My model is huge and I don't want to return a large amount of the data every time.
Yes, creating non-entity types is possible, using JPA constructor expressions i.e. the NEW keyword:
List<DTO> dtos = em.createQuery("SELECT NEW com.example.DTO( o.title, o.version) FROM Entity o").getResultList();
The DTO must have a constructor with all the relevant fields.
There is no need for casting.
I created my model using Db Context Generator, using EF 4.
My model is like this:
Program Table:
ID
Name
Group Table:
ID
Name
ProgramID (Associated to Program.ID)
I want to display these columns in my grid:
Program.Name - Group.Name
But grdGroups.DataSource = db.Groups.ToList()
doesn't return Program.Name
When I try to this I get ObjectDisposedException.
Partial Public Class Group
Public ReadOnly Property ProgramName() As String
Get
Return Program.Name
End Get
End Property
End Class
What's the best way to return the Program.Name to include it in the grid datasource?
When I try to this I get
ObjectDisposedException
The problem is lazy loading - EF did not materialize the related Program entity, hence when you try to access Program.Name it will try and re-query the DB, but the context has been disposed at this point, so you get an exception.
You can use an Include() query when you retrieve your Group entity, to specify that you also want to load the related Program entity, i.e. :
var groups = context.Groups.Include(x => x.Program);
I have an object that has been populated with the contents of four different related entities. However i have another entity in which i cannot include as part of the query due to it not being related in the navigation properites directly to the IQueryable table i am pulling. The entity i am trying to include is related to one of the four different entities that have been included successfully.
Is there a way to include(during db hit or afterwards) this entity as part of the overall object i am creating?
Here is an example of what my calls look like to build the CARTITEM object:
public List<CARTITEM> ListCartItem(Guid cartId)
{
//Create the Entity object
List<CARTITEM> itemInfo = null;
using (Entities webStoreContext = new Entities())
{
//Invoke the query
itemInfo = WebStoreDelegates.selectCartItems.Invoke(webStoreContext).ByCartID(cartId).ToList();
}
//Return the result set
return itemInfo;
}
here is the selectCartItems filter(Where i would normally do the includes):
public static Func<Entities, IQueryable<CARTITEM>> selectCartItems =
CompiledQuery.Compile<Entities, IQueryable<CARTITEM>>(
(cart) => from c in cart.CARTITEM.Include("ITEM").Include("SHIPPINGOPTION").Include("RELATEDITEM").Include("PROMOTION")
select c);
from this i have my CARTITEM object. Problem is i want to include the PROMOTIONTYPE table in this object, but since the CARTIEM entity doesn't have a navigation property directly to the PROMOTIONTYPE table i get an error.
Let me know if you need any more clarification.
Thanks,
Billy
You can use join and if it is the same database and server it should generate the join in SQL and do it all in one call...
LinqToEnties join example