-->
These old forums are deprecated now and set to read-only. We are waiting for you on our new forums!
More modern, Discourse-based and with GitHub/Google/Twitter authentication built-in.

All times are UTC - 5 hours [ DST ]



Forum locked This topic is locked, you cannot edit posts or make further replies.  [ 10 posts ] 
Author Message
 Post subject: Java Heap space - a never ending story
PostPosted: Wed Nov 07, 2007 4:13 pm 
Newbie

Joined: Wed Nov 07, 2007 3:58 pm
Posts: 15
Hi,

well i have read all the other topics about Java heap space problems and there seams not to be any solution.

In my project i have 100 Entities (Tables) that are using annotations. Some of these entities containing collections that are used in bidirectional mappings (ManyToOne and OneToMany). I have counted about 300 Sets in all classes. So far so good.
JUnit Test Case starts up, all tables are generated automatically.

BUT now i have added another entity that should be a wrapper of all other entities what means that the new entity class contains a Set for every existing entity with a bidirectional mapping.

If i wrap 5 entities in the new class - all works fine, but 100 entities are to much for hibernate/spring/eclipse.

I have already set the needed parameters in the eclipse.ini:
-vmargs
-XX:MaxPermSize=512m
-Xms1024m
-Xmx1024m

but every time INFO SessionFactoryImpl:161 - building session factory
is called i can wait 1 minute and get this ****** heap - out of memory error. What kind of a supercomputer must i own to get the schema working ?

Regards Tobias


Top
 Profile  
 
 Post subject:
PostPosted: Thu Nov 08, 2007 2:49 am 
Regular
Regular

Joined: Tue Jan 03, 2006 9:20 am
Posts: 74
sounds like you're trying to read your entire database in one single operation.
That's most likely what's causing your memory problems.


Top
 Profile  
 
 Post subject:
PostPosted: Thu Nov 08, 2007 3:43 am 
Newbie

Joined: Wed Nov 07, 2007 3:58 pm
Posts: 15
jwenting wrote:
sounds like you're trying to read your entire database in one single operation.
That's most likely what's causing your memory problems.


I would be happy if i would read something from the database. The Exception occurs when he creates the scheme. How else should i create the scheme using JPA Annotations ?



Caused by:
java.lang.OutOfMemoryError: Java heap space
at java.lang.AbstractStringBuilder.expandCapacity(AbstractStringBuilder.java:99)
at java.lang.AbstractStringBuilder.append(AbstractStringBuilder.java:393)
at java.lang.StringBuffer.append(StringBuffer.java:225)
at org.hibernate.loader.JoinWalker.selectString(JoinWalker.java:953)
at org.hibernate.loader.collection.OneToManyJoinWalker.initStatementString(OneToManyJoinWalker.java:99)
at org.hibernate.loader.collection.OneToManyJoinWalker.<init>(OneToManyJoinWalker.java:72)
at org.hibernate.loader.collection.OneToManyLoader.<init>(OneToManyLoader.java:53)
at org.hibernate.loader.collection.OneToManyLoader.<init>(OneToManyLoader.java:40)
at org.hibernate.loader.collection.OneToManyLoader.<init>(OneToManyLoader.java:31)
at org.hibernate.loader.collection.BatchingCollectionInitializer.createBatchingOneToManyInitializer(BatchingCollectionInitializer.java:72)
at org.hibernate.persister.collection.OneToManyPersister.createCollectionInitializer(OneToManyPersister.java:319)
at org.hibernate.persister.collection.AbstractCollectionPersister.postInstantiate(AbstractCollectionPersister.java:541)
at org.hibernate.impl.SessionFactoryImpl.<init>(SessionFactoryImpl.java:294)
at org.hibernate.cfg.Configuration.buildSessionFactory(Configuration.java:1294)
at org.hibernate.cfg.AnnotationConfiguration.buildSessionFactory(AnnotationConfiguration.java:915)
at org.hibernate.ejb.Ejb3Configuration.buildEntityManagerFactory(Ejb3Configuration.java:730)
at org.hibernate.ejb.HibernatePersistence.createContainerEntityManagerFactory(HibernatePersistence.java:127)


Top
 Profile  
 
 Post subject:
PostPosted: Thu Nov 08, 2007 4:11 am 
Regular
Regular

Joined: Tue Jan 03, 2006 9:20 am
Posts: 74
make sure you don't have a circular dependency between your JPA mapped beans.
Your stacktrace looks like a StringBuilder running out of space, which (I'm not sure, you'd have to look in the Hibernate sources) seems to me to be the result of a really massive SQL query.
The most likely cause for that is something recursive happening, like a circular dependency.


Top
 Profile  
 
 Post subject:
PostPosted: Thu Nov 08, 2007 6:15 am 
Newbie

Joined: Wed Nov 07, 2007 3:58 pm
Posts: 15
Hi,

I have just created an ANT build.xml file that uses hbm2ddl and write the CREATE and ALTER commands to a file. I can execute this task without any errors in 20 secs. :)

jwenting wrote:
seems to me to be the result of a really massive SQL query.

Well - YES - the sql-ddl textfile is about 147kb

So i don't think the problem results from my entities - what do you mean ?

I don't know if this is an Hibernate Problem - i don't think it is related to an eclipse bug, because i got the same error deploying my *.war in tomcat.

Next, I will configure my ANT script to export the tables directly to the database - i am really interested if this would work.


Top
 Profile  
 
 Post subject:
PostPosted: Thu Nov 08, 2007 6:40 am 
Newbie

Joined: Wed Nov 07, 2007 3:58 pm
Posts: 15
Hi,

I have a good and a bad message. First the good one:
The Ant task can create the database scheme in 1min22sec :)

Now the bad message:
I thought that hibernate should start up correctly now, because all the tables are already created... BUT i get the same Exception in the building session factory step like before.

Caused by: java.lang.OutOfMemoryError: Java heap space
at java.lang.String.<init>(Unknown Source)
at java.lang.StringBuffer.toString(Unknown Source)
at org.hibernate.sql.Select.toStatementString(Select.java:75)
at org.hibernate.loader.collection.OneToManyJoinWalker.initStatementString(OneToManyJoinWalker.java:121)
at org.hibernate.loader.collection.OneToManyJoinWalker.<init>(OneToManyJoinWalker.java:72)
at org.hibernate.loader.collection.OneToManyLoader.<init>(OneToManyLoader.java:53)
at org.hibernate.loader.collection.OneToManyLoader.<init>(OneToManyLoader.java:40)
at org.hibernate.loader.collection.OneToManyLoader.<init>(OneToManyLoader.java:31)
at org.hibernate.loader.collection.BatchingCollectionInitializer.createBatchingOneToManyInitializer(BatchingCollectionInitializer.java:72)
at org.hibernate.persister.collection.OneToManyPersister.createCollectionInitializer(OneToManyPersister.java:319)
at org.hibernate.persister.collection.AbstractCollectionPersister.postInstantiate(AbstractCollectionPersister.java:541)
at org.hibernate.impl.SessionFactoryImpl.<init>(SessionFactoryImpl.java:294)
at org.hibernate.cfg.Configuration.buildSessionFactory(Configuration.java:1294)
at org.hibernate.cfg.AnnotationConfiguration.buildSessionFactory(AnnotationConfiguration.java:915)
at org.hibernate.ejb.Ejb3Configuration.buildEntityManagerFactory(Ejb3Configuration.java:730)
at org.hibernate.ejb.HibernatePersistence.createContainerEntityManagerFactory(HibernatePersistence.java:127)
at org.springframework.orm.jpa.LocalContainerEntityManagerFactoryBean.createNativeEntityManagerFactory(LocalContainerEntityManagerFactoryBean.java:218)
at org.springframework.orm.jpa.AbstractEntityManagerFactoryBean.afterPropertiesSet(AbstractEntityManagerFactoryBean.java:251)


Maybe there is a hibernate developer or forum leader out there who can help ?

Or does anybody know a less heap space consuming method to group all entities in a single one. That means that i would like to have an Instance object that saves a specific configuration of used entities in this instance. An instance may contain all defined entities unbounded times (except itself). Therefore i have created an Instance-Entity-Class that had a Set for each Entity-Class with a OneToMany Annotation, and the refereced class Set<Entity-Class> contains a ManyToOne Annotation.
=> Bidirectional Mapping
The bidirectional Property is not really needed but nice to have... a unidirectional sollution would solve the problem as well (unidirectional: Instance can access its Entities)


Last edited by anstetts on Thu Nov 08, 2007 6:52 am, edited 1 time in total.

Top
 Profile  
 
 Post subject:
PostPosted: Thu Nov 08, 2007 6:49 am 
Regular
Regular

Joined: Wed Apr 25, 2007 11:44 pm
Posts: 59
check for lazy dude


Top
 Profile  
 
 Post subject:
PostPosted: Thu Nov 08, 2007 6:54 am 
Regular
Regular

Joined: Tue Jan 03, 2006 9:20 am
Posts: 74
The problem is that the SQL for some statement is exploding in size until it no longer fits in the memory available to a StringBuilder (or indeed the JVM).

It's apparently a select statement, so executing the DDL isn't going to matter.
Lazy loading would, as it should spread out the query over multiple requests.
But if I'm correct and you have circular dependencies somewhere it would still cause problems. These could be either StackOverflowError or OutOfMemoryError depending on how and when it blows up.


Top
 Profile  
 
 Post subject:
PostPosted: Thu Nov 08, 2007 7:09 am 
Newbie

Joined: Wed Nov 07, 2007 3:58 pm
Posts: 15
msj4u wrote:
check for lazy dude


:) Added fetch=javax.persistence.FetchType.LAZY to every OneToMany and ManyToOne annotation and well - IT WORKS

Thx a lot to msj4u and jwenting


Top
 Profile  
 
 Post subject: Re: Java Heap space - a never ending story
PostPosted: Thu Oct 01, 2009 5:22 am 
Regular
Regular

Joined: Thu May 07, 2009 5:56 am
Posts: 94
Location: Toulouse, France
I don't think that a circular dependency is the only cause of this problem...In fact, entities with circular references and EAGER (fetch mode) associations produces a more complex (and big) sql select.

If you change your fetch mode to LAZY for each many-to-one or one-to-one association you'll get a simple sql select and it may solve OutOfMemory problem.

But, don't forget also when you active hibernate.default_batch_fetch_size property, Hibernate holds a "batch_fetch_size" SQL selects. for exemple:
select foo_id, foo_attribute where foo_id in (?)
select foo_id, foo_attribute where foo_id in (?,?)
...
select foo_id, foo_attribute where foo_id in (?, ?,..., default_batch_fetch_size)

It's take a lot of memory!! So, if you have many entities and your fetch mode is EAGER it's better disable default_batch_fetch_size or put a lower value for this property.

_________________
everything should be made as simple as possible, but not simpler (AE)


Top
 Profile  
 
Display posts from previous:  Sort by  
Forum locked This topic is locked, you cannot edit posts or make further replies.  [ 10 posts ] 

All times are UTC - 5 hours [ DST ]


You cannot post new topics in this forum
You cannot reply to topics in this forum
You cannot edit your posts in this forum
You cannot delete your posts in this forum

Search for:
© Copyright 2014, Red Hat Inc. All rights reserved. JBoss and Hibernate are registered trademarks and servicemarks of Red Hat, Inc.