-
1. Re: Complex Search Results - return object identifiers inste
twocoasttb Jun 21, 2007 6:48 PM (in response to jfrankman)I'm no expert, but this makes sense to me. I'm planning on doing something similar in my application when selecting sets objects with a deep object graph for display (and selection). Purists will no doubt howl, but I plan, in some cases, to create views to generate search results. A 'flat proxy POJO' (I don't know what else to call it) would be defined for each view. And from that proxy object, I'll get the id of the object the user is actually interested in, and go fetch it.
I haven't benchmarked any of this yet, but I expect the application would do much less work. Plus, I get more control over the SQL actually executed during the search. -
2. Re: Complex Search Results - return object identifiers inste
pmuir Jun 22, 2007 5:16 AM (in response to jfrankman)Not really. We have this wonderful thing called lazy fetching which makes the kind of pre-optimization you are planning largely useless. If you want to do things this way, why not just write your own ORM rather than use an existing one?
-
3. Re: Complex Search Results - return object identifiers inste
jfrankman Jun 22, 2007 9:55 AM (in response to jfrankman)I agree that lazy instantiation is the best way to go, but my problem with the lazy instantiation is that I have trouble keeping my objects in the session. My seam action classes call my business layer to get all objects:
i.e. List clients=clientService.findByLastName("Doe");
This works fine to display the search results, but when I click a detail row to go to the detail page I get lazy initialization errors:
client.getPolicies(); <-- produces lazy initialization error.
I think the problem is that the call to the entity manager is buried in my DAO layer and is not in the action itself. In other words, my action calls the business layer which in turn calls the DAO layer to get the object. Because the EntityManager is not in the action I get lazy initialization errors, is this correct? Am I going about this all wrong?
I know there must be a way to do this, but others have complained about this problem as well: http://www.jboss.com/index.html?module=bb&op=viewtopic&t=62275
I cannot quite understand how to keep the object in the session between pages I keep getting LazyInitialization errors on all subsequent pages. What am I doing wrong? -
4. Re: Complex Search Results - return object identifiers inste
pmuir Jun 22, 2007 10:04 AM (in response to jfrankman)Are you using a long running conversation with a conversation scoped (aka seam managed) persistence context?
-
5. Re: Complex Search Results - return object identifiers inste
jfrankman Jun 22, 2007 10:22 AM (in response to jfrankman)My entity bean has session scope:
@Table(name="FBCLIENT",schema="DB2ADMIN") @Name("client") @Scope(ScopeType.SESSION) public class ClientVO implements Serializable { private static final long serialVersionUID = 2285612284592204149L; private Long id; private String notes; private String clientType; private String memberNumber; private Set<ClientLocationVO> entityLocations = new HashSet<ClientLocationVO>(); private Set<PolicyVO> policies = new HashSet<PolicyVO>(); private String search; private DrivingDistance drivingDistance; private String homePhone; private String workPhone; private String cellPhone; private String pagerNo; private String email; private ClientVO parentClient; private List<ClientVO> clientMembers=new ArrayList<ClientVO>(); /** * @return the childMembers */ @OneToMany(mappedBy="parentClient",fetch=FetchType.LAZY) public List<ClientVO> getClientMembers() { return clientMembers; } /** * @return the parentClient */ @ManyToOne() @JoinColumn (name="parentclientid" ) public ClientVO getParentClient() { return parentClient; } ....
When I perform the search I do not use a conversation, just a stateless session bean:@Stateless @Name("search") public class SearchAction implements Search { @In Identity identity; @In private SearchVO searchvo; @In(create=true) private ClientService clientService; @In(create=true) private PolicyService policyService; @In(required=false) private FBWorker worker; @Out(required=false) private PolicyVO policy; public String performNameSearch() { searchResults = policyService.findPolicyHoldersByNameIncludeSubclients(searchvo.getSearchString()); searchvo.setSearchResults(searchResults); return "success"; } ...
When the user clicks the row in the datatable I then try and load the entire object by calling the lookupClientFromSearch method on my ClientAction stateful bean. :<h:commandLink value="#{searchResult.clientVO.fullName}" action="#{clientAction.lookupClientFromSearch}"/>
Inside the lookupclientFromSearch I am using a conversation:@Stateful @Name("clientAction") public class ClientActionImpl implements ClientAction { @In(create=true) private ClientService clientService; @In(required=false) @Out(required=false) ClientVO client; @In @Out(required=false) PolicyVO policy; @In(required=false) ClientVO subClient; @In(required=false) MasterSearchResultVO searchResult; @Begin(join=true) public String lookupClientFromSearch() { client=clientService.findClientByIdFetchGraph(searchResult.getClientVO().getId()); if (client instanceof PersonVO) { organizationFlag=false; personFlag=true; System.out.println("The Client is a PersonVO"); policy.getPolicyHolder(); } else if (client instanceof OrganizationVO) { organizationFlag=true; personFlag=false; System.out.println("The Client is a PersonVO"); } else { System.out.println("The Client is a only a ClientVO"); } return "success"; } @End ....