# Java > Gnral Java > Persistance des donnes >  Castor + gros fichier XML = java.lang.StackOverflowError

## spooon

Salut  tous ! 

Voici mon problme.
Je travaille sur un projet qui ncessite d'instancier des objets java  partir de fichiers XML. Castor fait exactement a.

Ma situation est assez simple.

J'utilise d'abord Castor pour crer un fichier XML : test.xml en faisant du marshalling(srialisation) d'un objet Person (celui des exemples du site de castor).
Ensuite, je fais l'inverse, et j'unmarshall (dsrialise) test.xml pour rcuprer un deuxime objet Person. Les deux sont identiques => Ok.

Le fichier test.xml gnr par le Marshaller :
<person>
<name>Ryan</name>
<date-of-birth>2000-10-10T00:00:00.000+02:00</date-of-birth>
</person>
a semble Ok.

Mais j'ai besoin de dsrialiser de GROS fichiers XML (~1Go) dans un environnement de production.
Donc, j'ajoute des gros nodes  mon fichier test.xml gnr plus haut, jusqu' ce que celui-ci fasse 1Go.
La structure du fichier reste la mme : 
<person>
<movement>.....</movement>
// pleins de nodes <movement> ici
<name>Ryan</name>
<date-of-birth>2000-10-10T00:00:00.000+02:00</date-of-birth>
</person>

Quand je dsrialise ce fichier de 1Go, j'attrape l'exception :
Exception in thread "Main Thread" java.lang.StackOverflowError
at org.exolab.castor.xml.Namespaces.getNamespaceURI(Namespaces.java:206)
...


Je n'utilise pas de fichier de mapping.
paramtres JVM :
-Xmx1024m.
-Taille de la JVM au moment du crash: 70Mo ~

Fichiers attachs : 
Person.java : L'objet Person vers lequel dsrialiser
TestIt.java : La classe de test
test.xml : Fichier gnr par la srialisation de l'objet Person, que j'ai ensuite dsrialis. Tout est Ok avec ce fichier.
112.xml : Fichier test.xml auquel j'ai ajout un node <movement>. dsrialisation Ok
Lorsque mon fichier 112.xml fait 1Go (en gros quand j'ajoute un bon paquet de nodes <movement> les uns derrire les autres, impossible de dsrialiser  ::(: 


Quelqu'un peut m'aider ou connait un outil permettant de faire de la dsrialisation de gros fichier tel que celui-l ? ?

----------


## spooon

Une petite ide ? Personne ? 
Une aide serait vraiment trs apprie.
Merci  ::):

----------


## JeitEmgie

> Une petite ide ? Personne ? 
> Une aide serait vraiment trs apprie.
> Merci


Un Parser SAX peut aider

mais tout dpend de la taille des "units/chunks" qu'il faut traiter
(mme avec un parser SAX si vous vous amusez  reconstruire tout l'arbre en mmoire vous pouvez retomber sur le problme du out-of-memory)

1 Gb peut-tre un gros objet (une "unit") de 1 Gb ou des milliers de petits objets traitables sparment

 vous d'analyser l'empreinte minimum de votre code : quel est le nombre d'objets inter-relis qu'il faut traiter en mme temps (garder ensemble en mmoire)  avant de pouvoir les oublier et passer au groupe suivant
(si vous ne pouvez pas sparer le traitement logique du fichier en lots, vous aurez de toute faon le problme - plus ou moins loin dans le traitement - quel que soit le type de parser)

c'est ce qui dterminera la taille mmoire minimum ncessaire  allouer au process et si cela excde ce que vous pouvez allouer sur votre plate-forme, c'est qu'il faut passer  autre chose

----------


## spooon

Je comprend tout  fait ! 
Cela voudrait dire qu'ici, mon unit <person> est trop grosse, ce qui n'est pas le cas de mes entits dans mon environnement de production, o les entit pouvant tre traits de faon unitaire font moins de 1Mo, mais son en trs grand nombre dans le fichier XML. 

Actuellement, mon application tourne avec une librairie Castor 0.9.7.
le fonctionnement est le suivant.
Le fichier  utiliser contient un grand nombre de <commande>, chacune devant tre traite sparment.
Les commandes instancies sont mise dans un pull de commande.
Ce pull de commande alimente un handler qui va traiter une  une les commandes. 
Dans l'ordre, les tapes sont : 

1/ Unmarshalling du fichier de 500Mo~ (fichier qui va dpasser les 1Go  la prochaine version), et instaniation des objets commandes
2/ Traitement des commandes (criture en base etc...)

Si j'ai bien compris ce que tu me dis JeitEmgie, il est possible de commander le comportement du parser de Castor. Serait-il possible que le parser s'arrte dans son instanciation, et "attende" que le nombre de commande dans le pull de commandes disponibles passe en dessous d'un seuil, avant de le ralimenter avec de nouvelles commandes fraichement parses, et donc d'utiliser moins de mmoire ?

----------


## JeitEmgie

> Je comprend tout  fait ! 
> Cela voudrait dire qu'ici, mon unit <person> est trop grosse, ce qui n'est pas le cas de mes entits dans mon environnement de production, o les entit pouvant tre traits de faon unitaire font moins de 1Mo, mais son en trs grand nombre dans le fichier XML. 
> 
> Actuellement, mon application tourne avec une librairie Castor 0.9.7.
> le fonctionnement est le suivant.
> Le fichier  utiliser contient un grand nombre de <commande>, chacune devant tre traite sparment.
> Les commandes instancies sont mise dans un pull de commande.
> Ce pull de commande alimente un handler qui va traiter une  une les commandes. 
> Dans l'ordre, les tapes sont : 
> ...


je n'utilises pas Castor donc je n'en sais rien

mais un parser de type SAX cd un parser qui appelle vos callbacks sur les lments XML qu'il rencontre, vous permet de grer votre machine d'tats et ainsi de contrler l'empreinte mmoire laisse par vos structures

(par opposition  un parser DOM qui charge tout le document en mmoire)

----------


## spooon

Merci JeitEmgie pour ton aide. Ceci m'claire un peu.

Je vais maintenant me documenter sur la manire de piloter le parser de Castor, afin d'viter l'explosion de l'utilisation mmoire. 
si quelqu'un sait comment faire cela, je suis extrmement intress.

----------


## spooon

Le problme ne venait pas de castor, mais de la manire de l'utiliser.
Aujourd'hui, j'utilise un stringbuffer pour dcouper le fichier xml en petits noeuds que je traite sparment, plutot que de demander  castor de crer un gros objet contenant le rsultat de la dsrialisation du fichier xml entier de dpart.

En pilotant castor avec un pool, j'arrive  diminuer la RAM utilise de 99%, victoire donc.

Fonction pour dcouper mon XML en petits noeuds : 
getElement(reader, "mouvement", log)
ramne un string contenant le noeud <mouvement>[...]</mouvement> 


```

```

ensuite, je traite mon string : 


```

```

Et voil
Merci pour l'aide.

----------

