[hibernate-commits] Hibernate SVN: r14074 - in core/trunk/documentation/manual/fr-FR/src/main: docbook and 2 other directories.

hibernate-commits at lists.jboss.org hibernate-commits at lists.jboss.org
Tue Oct 9 14:28:37 EDT 2007


Author: steve.ebersole at jboss.com
Date: 2007-10-09 14:28:36 -0400 (Tue, 09 Oct 2007)
New Revision: 14074

Added:
   core/trunk/documentation/manual/fr-FR/src/main/docbook/Hibernate_Reference.xml
   core/trunk/documentation/manual/fr-FR/src/main/docbook/content/
   core/trunk/documentation/manual/fr-FR/src/main/docbook/content/architecture.xml
   core/trunk/documentation/manual/fr-FR/src/main/docbook/content/association_mapping.xml
   core/trunk/documentation/manual/fr-FR/src/main/docbook/content/basic_mapping.xml
   core/trunk/documentation/manual/fr-FR/src/main/docbook/content/batch.xml
   core/trunk/documentation/manual/fr-FR/src/main/docbook/content/best_practices.xml
   core/trunk/documentation/manual/fr-FR/src/main/docbook/content/collection_mapping.xml
   core/trunk/documentation/manual/fr-FR/src/main/docbook/content/component_mapping.xml
   core/trunk/documentation/manual/fr-FR/src/main/docbook/content/configuration.xml
   core/trunk/documentation/manual/fr-FR/src/main/docbook/content/events.xml
   core/trunk/documentation/manual/fr-FR/src/main/docbook/content/example_mappings.xml
   core/trunk/documentation/manual/fr-FR/src/main/docbook/content/example_parentchild.xml
   core/trunk/documentation/manual/fr-FR/src/main/docbook/content/example_weblog.xml
   core/trunk/documentation/manual/fr-FR/src/main/docbook/content/filters.xml
   core/trunk/documentation/manual/fr-FR/src/main/docbook/content/inheritance_mapping.xml
   core/trunk/documentation/manual/fr-FR/src/main/docbook/content/performance.xml
   core/trunk/documentation/manual/fr-FR/src/main/docbook/content/persistent_classes.xml
   core/trunk/documentation/manual/fr-FR/src/main/docbook/content/preface.xml
   core/trunk/documentation/manual/fr-FR/src/main/docbook/content/query_criteria.xml
   core/trunk/documentation/manual/fr-FR/src/main/docbook/content/query_hql.xml
   core/trunk/documentation/manual/fr-FR/src/main/docbook/content/query_sql.xml
   core/trunk/documentation/manual/fr-FR/src/main/docbook/content/session_api.xml
   core/trunk/documentation/manual/fr-FR/src/main/docbook/content/toolset_guide.xml
   core/trunk/documentation/manual/fr-FR/src/main/docbook/content/transactions.xml
   core/trunk/documentation/manual/fr-FR/src/main/docbook/content/tutorial.xml
   core/trunk/documentation/manual/fr-FR/src/main/docbook/content/xml.xml
   core/trunk/documentation/manual/fr-FR/src/main/docbook/images/
   core/trunk/documentation/manual/fr-FR/src/main/docbook/images/AuthorWork.png
   core/trunk/documentation/manual/fr-FR/src/main/docbook/images/AuthorWork.zargo
   core/trunk/documentation/manual/fr-FR/src/main/docbook/images/CustomerOrderProduct.png
   core/trunk/documentation/manual/fr-FR/src/main/docbook/images/CustomerOrderProduct.zargo
   core/trunk/documentation/manual/fr-FR/src/main/docbook/images/EmployerEmployee.png
   core/trunk/documentation/manual/fr-FR/src/main/docbook/images/EmployerEmployee.zargo
   core/trunk/documentation/manual/fr-FR/src/main/docbook/images/full_cream.png
   core/trunk/documentation/manual/fr-FR/src/main/docbook/images/full_cream.svg
   core/trunk/documentation/manual/fr-FR/src/main/docbook/images/hibernate_logo_a.png
   core/trunk/documentation/manual/fr-FR/src/main/docbook/images/lite.png
   core/trunk/documentation/manual/fr-FR/src/main/docbook/images/lite.svg
   core/trunk/documentation/manual/fr-FR/src/main/docbook/images/overview.png
   core/trunk/documentation/manual/fr-FR/src/main/docbook/images/overview.svg
   core/trunk/documentation/manual/fr-FR/src/main/docbook/legal_notice.xml
   core/trunk/documentation/manual/fr-FR/src/main/docbook/translators.xml
Removed:
   core/trunk/documentation/manual/fr-FR/src/main/docbook/master.xml
   core/trunk/documentation/manual/fr-FR/src/main/docbook/modules/
   core/trunk/documentation/manual/fr-FR/src/main/resources/
Log:
new docbook layout (prep for translations migration to PO)

Added: core/trunk/documentation/manual/fr-FR/src/main/docbook/Hibernate_Reference.xml
===================================================================
--- core/trunk/documentation/manual/fr-FR/src/main/docbook/Hibernate_Reference.xml	                        (rev 0)
+++ core/trunk/documentation/manual/fr-FR/src/main/docbook/Hibernate_Reference.xml	2007-10-09 18:28:36 UTC (rev 14074)
@@ -0,0 +1,72 @@
+<?xml version='1.0' encoding="iso-8859-1"?>
+<!DOCTYPE book PUBLIC "-//OASIS//DTD DocBook XML V4.5//EN" "http://www.oasis-open.org/docbook/xml/4.5/docbookx.dtd" [
+        <!ENTITY versionNumber "3.3.0.alpha1">
+        <!ENTITY copyrightYear "2004">
+        <!ENTITY copyrightHolder "Red Hat Middleware, LLC.">
+]>
+
+<book>
+
+    <bookinfo>
+        <title>HIBERNATE - Persistance relationnelle en Java standard</title>
+        <subtitle>Documentation de référence d'Hibernate</subtitle>
+        <releaseinfo>&versionNumber;</releaseinfo>
+        <productnumber>&versionNumber;</productnumber>
+        <issuenum>1</issuenum>
+        <mediaobject>
+            <imageobject role="fo">
+                <imagedata fileref="images/hibernate_logo_a.png" align="center" />
+            </imageobject>
+            <imageobject role="html">
+                <imagedata fileref="images/hibernate_logo_a.png" depth="3cm" />
+            </imageobject>
+        </mediaobject>
+        <copyright>
+            <year>&copyrightYear;</year>
+            <holder>&copyrightHolder;</holder>
+        </copyright>
+        <xi:include href="translators.xml" xmlns:xi="http://www.w3.org/2001/XInclude" />
+        <xi:include href="legal_notice.xml" xmlns:xi="http://www.w3.org/2001/XInclude" />
+    </bookinfo>
+
+    <toc/>
+
+    <xi:include href="content/preface.xml" xmlns:xi="http://www.w3.org/2001/XInclude" />
+
+	<xi:include href="content/tutorial.xml" xmlns:xi="http://www.w3.org/2001/XInclude" />
+
+	<xi:include href="content/architecture.xml" xmlns:xi="http://www.w3.org/2001/XInclude" />
+
+	<xi:include href="content/configuration.xml" xmlns:xi="http://www.w3.org/2001/XInclude" />
+
+	<xi:include href="content/persistent_classes.xml" xmlns:xi="http://www.w3.org/2001/XInclude" />
+
+    <xi:include href="content/basic_mapping.xml" xmlns:xi="http://www.w3.org/2001/XInclude" />
+    <xi:include href="content/collection_mapping.xml" xmlns:xi="http://www.w3.org/2001/XInclude" />
+    <xi:include href="content/association_mapping.xml" xmlns:xi="http://www.w3.org/2001/XInclude" />
+    <xi:include href="content/component_mapping.xml" xmlns:xi="http://www.w3.org/2001/XInclude" />
+    <xi:include href="content/inheritance_mapping.xml" xmlns:xi="http://www.w3.org/2001/XInclude" />
+
+    <xi:include href="content/session_api.xml" xmlns:xi="http://www.w3.org/2001/XInclude" />
+    <xi:include href="content/transactions.xml" xmlns:xi="http://www.w3.org/2001/XInclude" />
+    <xi:include href="content/events.xml" xmlns:xi="http://www.w3.org/2001/XInclude" />
+    <xi:include href="content/batch.xml" xmlns:xi="http://www.w3.org/2001/XInclude" />
+
+    <xi:include href="content/query_hql.xml" xmlns:xi="http://www.w3.org/2001/XInclude" />
+    <xi:include href="content/query_criteria.xml" xmlns:xi="http://www.w3.org/2001/XInclude" />
+    <xi:include href="content/query_sql.xml" xmlns:xi="http://www.w3.org/2001/XInclude" />
+    <xi:include href="content/filters.xml" xmlns:xi="http://www.w3.org/2001/XInclude" />
+    <xi:include href="content/xml.xml" xmlns:xi="http://www.w3.org/2001/XInclude" />
+
+    <xi:include href="content/performance.xml" xmlns:xi="http://www.w3.org/2001/XInclude" />
+
+    <xi:include href="content/toolset_guide.xml" xmlns:xi="http://www.w3.org/2001/XInclude" />
+
+    <xi:include href="content/example_parentchild.xml" xmlns:xi="http://www.w3.org/2001/XInclude" />
+    <xi:include href="content/example_weblog.xml" xmlns:xi="http://www.w3.org/2001/XInclude" />
+    <xi:include href="content/example_mappings.xml" xmlns:xi="http://www.w3.org/2001/XInclude" />
+
+    <xi:include href="content/best_practices.xml" xmlns:xi="http://www.w3.org/2001/XInclude" />
+
+</book>
+

Copied: core/trunk/documentation/manual/fr-FR/src/main/docbook/content/architecture.xml (from rev 14070, core/trunk/documentation/manual/fr-FR/src/main/docbook/modules/architecture.xml)
===================================================================
--- core/trunk/documentation/manual/fr-FR/src/main/docbook/content/architecture.xml	                        (rev 0)
+++ core/trunk/documentation/manual/fr-FR/src/main/docbook/content/architecture.xml	2007-10-09 18:28:36 UTC (rev 14074)
@@ -0,0 +1,366 @@
+<?xml version="1.0" encoding="iso-8859-1"?>
+<!--
+  ~ Copyright (c) 2007, Red Hat Middleware, LLC. All rights reserved.
+  ~
+  ~ This copyrighted material is made available to anyone wishing to use, modify,
+  ~ copy, or redistribute it subject to the terms and conditions of the GNU
+  ~ Lesser General Public License, v. 2.1. This program is distributed in the
+  ~ hope that it will be useful, but WITHOUT A WARRANTY; without even the implied
+  ~ warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
+  ~ Lesser General Public License for more details. You should have received a
+  ~ copy of the GNU Lesser General Public License, v.2.1 along with this
+  ~ distribution; if not, write to the Free Software Foundation, Inc.,
+  ~ 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
+  ~
+  ~ Red Hat Author(s): Steve Ebersole
+  -->
+<chapter id="architecture">
+
+    <title>Architecture</title>
+
+    <sect1 id="architecture-overview" revision="1">
+        <title>Généralités</title>
+        
+        <para>
+            Voici une vue (très) haut niveau de l'architecture d'Hibernate :
+        </para>
+
+        <mediaobject>
+            <imageobject role="fo">
+                <imagedata fileref="../images/overview.svg" format="SVG" align="center"/>
+            </imageobject>
+            <imageobject role="html">
+                <imagedata fileref="../images/overview.gif" format="GIF" align="center"/>
+            </imageobject>
+        </mediaobject>
+
+        <para>
+            Ce diagramme montre Hibernate utilisant une base de données et des données
+            de configuration pour fournir un service de persistance (et des objets
+            persistants) à l'application.
+        </para>
+
+        <para>
+            Nous aimerions décrire une vue plus détaillée de l'architecture. Malheureusement,
+            Hibernate est flexible et supporte différentes approches. Nous allons en
+            montrer les deux extrêmes. L'architecture légère laisse l'application fournir
+            ses propres connexions JDBC et gérer ses propres transactions. Cette approche
+            utilise le minimum des APIs Hibernate :
+        </para>
+
+        <mediaobject>
+            <imageobject role="fo">
+                <imagedata fileref="../images/lite.svg" format="SVG" align="center"/>
+            </imageobject>
+            <imageobject role="html">
+                <imagedata fileref="../images/lite.gif" format="GIF" align="center"/>
+            </imageobject>
+        </mediaobject>
+
+        <para>
+            L'architecture la plus complète abstrait l'application des APIs JDBC/JTA 
+            sous-jacentes et laisse Hibernate s'occuper des détails.
+        </para>
+
+        <mediaobject>
+            <imageobject role="fo">
+                <imagedata fileref="../images/full_cream.svg" format="SVG" align="center"/>
+            </imageobject>
+            <imageobject role="html">
+                <imagedata fileref="../images/full_cream.gif" format="GIF" align="center"/>
+            </imageobject>
+        </mediaobject>
+
+        <para>
+            Voici quelques définitions des objets des diagrammes :
+
+            <variablelist spacing="compact">
+                <varlistentry>
+                    <term>SessionFactory (<literal>org.hibernate.SessionFactory</literal>)</term>
+                    <listitem>
+                        <para>
+                            Un cache threadsafe (immuable) des mappings vers une (et une seule) base 
+                            de données. Une factory (fabrique) de <literal>Session</literal> et un client
+                            de <literal>ConnectionProvider</literal>. Peut contenir un cache optionnel de
+                            données (de second niveau) qui est réutilisable entre les différentes transactions
+                            que cela soit au sein du même processus (JVLM) ou par plusieurs n½uds d'un cluster.
+                        </para>
+                    </listitem>
+                </varlistentry>
+                <varlistentry>
+                    <term>Session (<literal>org.hibernate.Session</literal>)</term>
+                    <listitem>
+                        <para>
+                            Un objet mono-threadé, à durée de vie courte, qui représente une conversation
+                            entre l'application et l'entrepôt de persistance. Encapsule une connexion JDBC.
+                            Factory (fabrique) des objets <literal>Transaction</literal>. Contient un cache
+                            (de premier niveau) des objets persistants, ce cache est obligatoire. Il est 
+                            utilisé lors de la navigation dans le graphe d'objets ou lors de la récupération
+                            d'objets par leur identifiant.
+                        </para>
+                    </listitem>
+                </varlistentry>
+                <varlistentry>
+                    <term>Objets et Collections persistants</term>
+                    <listitem>
+                        <para>
+                            Objets mono-threadés à vie courte contenant l'état de persistance
+                            et la fonction métier. Ceux-ci sont en général les objets de type JavaBean
+                            (ou POJOs) ; la seule particularité est qu'ils sont associés avec une (et
+                            une seule) <literal>Session</literal>. Dès que la <literal>Session</literal>
+                            est fermée, ils seront détachés et libres d'être utilisés par n'importe laquelle
+                            des couches de l'application (ie. de et vers la présentation en tant que Data 
+                            Transfer Objects - DTO : objet de transfert de données).
+                        </para>
+                    </listitem>
+                </varlistentry>
+                <varlistentry>
+                    <term>Objets et collections transients</term>
+                    <listitem>
+                        <para>
+                            Instances de classes persistantes qui ne sont actuellement pas associées à
+                            une <literal>Session</literal>. Elles ont pu être instanciées par l'application
+                            et ne pas avoir (encore) été persistées ou elle ont pu être instanciées par
+                            une <literal>Session</literal> fermée.
+                        </para>
+                    </listitem>
+                </varlistentry>
+                <varlistentry>
+                    <term>Transaction (<literal>org.hibernate.Transaction</literal>)</term>
+                    <listitem>
+                        <para>
+                            (Optionnel) Un objet mono-threadé à vie courte utilisé par l'application
+                            pour définir une unité de travail atomique. Abstrait l'application des
+                            transactions sous-jacentes qu'elles soient JDBC, JTA ou CORBA. Une
+                            <literal>Session</literal> peut fournir plusieurs <literal>Transaction</literal>s
+                            dans certains cas. Toutefois, la délimitation des transactions, via l'API d'Hibernate
+                            ou par la <literal>Transaction</literal> sous-jacente, n'est jamais optionnelle!
+                        </para>
+                    </listitem>
+                </varlistentry>
+                <varlistentry>
+                    <term>ConnectionProvider (<literal>org.hibernate.connection.ConnectionProvider</literal>)</term>
+                    <listitem>
+                        <para>
+                            (Optionnel) Une fabrique de (pool de) connexions JDBC. Abstrait l'application
+                            de la <literal>Datasource</literal> ou du <literal>DriverManager</literal> sous-jacent.
+                            Non exposé à l'application, mais peut être étendu/implémenté par le développeur.
+                        </para>
+                    </listitem>
+                </varlistentry>
+                <varlistentry>
+                    <term>TransactionFactory (<literal>org.hibernate.TransactionFactory</literal>)</term>
+                    <listitem>
+                        <para>
+                            (Optionnel) Une fabrique d'instances de <literal>Transaction</literal>. Non
+                            exposé à l'application, mais peut être étendu/implémenté par le développeur.
+                        </para>
+                    </listitem>
+                </varlistentry>
+                <varlistentry>
+                    <term><emphasis>Interfaces d'extension</emphasis></term>
+                    <listitem>
+                        <para>
+                            Hibernate fournit de nombreuses interfaces d'extensions optionnelles que 
+                            vous pouvez implémenter pour personnaliser le comportement de votre couche de persistance.
+                            Reportez vous à la documentation de l'API pour plus de détails.
+                        </para>
+                    </listitem>
+                </varlistentry>
+            </variablelist>
+        </para>
+
+        <para>
+            Dans une architecture légère, l'application n'aura pas à utiliser les APIs
+            <literal>Transaction</literal>/<literal>TransactionFactory</literal>
+            et/ou n'utilisera pas les APIs <literal>ConnectionProvider</literal>
+            pour utiliser JTA ou JDBC.
+        </para>
+    </sect1>
+
+    <sect1 id="architecture-states" revision="1">
+        <title>Etats des instances</title>
+        <para>
+            Une instance d'une classe persistante peut être dans l'un des trois états suivants,
+            définis par rapport à un <emphasis>contexte de persistance</emphasis>.
+            L'objet <literal>Session</literal> d'hibernate correspond à ce concept de 
+            contexte de persistance :
+        </para>
+        
+       <variablelist spacing="compact">
+            <varlistentry>
+                <term>passager (transient)</term>
+                <listitem>
+                    <para>
+                        L'instance n'est pas et n'a jamais été associée à un contexte
+                        de persistance. Elle ne possède pas d'identité persistante (valeur de clé primaire)
+                    </para>
+                </listitem>
+            </varlistentry>
+            <varlistentry>
+                <term>persistant</term>
+                <listitem>
+                    <para>
+                        L'instance est associée au contexte de persistance.
+                        Elle possède une identité persistante (valeur de clé primaire)
+                        et, peut-être, un enregistrement correspondant dans la base.
+                        Pour un contexte de persistance particulier, Hibernate
+                        <emphasis>garantit</emphasis> que l'identité persistante
+                        est équivalente à l'identité Java (emplacement mémoire de l'objet)
+                    </para>
+                </listitem>
+            </varlistentry>
+            <varlistentry>
+                <term>détaché</term>
+                <listitem>
+                    <para>
+                        L'instance a été associée au contexte de persistance mais ce
+                        contexte a été fermé, ou l'instance a été sérialisée vers un
+                        autre processus. Elle possède une identité persistante et
+                        peut-être un enregistrement correspondant dans la base.
+                        Pour des instances détachées, Hibernate ne donne aucune
+                        garantie sur la relation entre l'identité persistante et
+                        l'identité Java.
+                    </para>
+                </listitem>
+            </varlistentry>
+        </variablelist>
+    </sect1>    
+
+    <sect1 id="architecture-jmx" revision="1">
+        <title>Intégration JMX</title>
+        <para>
+            JMX est le standard J2EE de gestion des composants Java. 
+            Hibernate peut être géré via un service JMX standard. Nous fournissons une implémentation
+            d'un MBean dans la distribution : <literal>org.hibernate.jmx.HibernateService</literal>.
+        </para>
+        
+        <para>
+            Pour avoir un exemple sur la manière de déployer Hibernate en tant que service JMX dans le
+            serveur d'application JBoss Application Server, référez vous au guide utilisateur JBoss (JBoss User Guide).
+            Si vous déployez Hibernate via JMX sur JBoss AS, vous aurez également les bénéfices suivants :
+        </para>
+        <itemizedlist>
+            <listitem>
+                <para>
+                    <emphasis>Gestion de la session :</emphasis> Le cycle de vie de la <literal>Session</literal>
+                    Hibernate peut être automatiquement limitée à la portée d'une transaction JTA.
+                    Cela signifie que vous n'avez plus besoin d'ouvrir et de fermer la <literal>Session</literal>
+                    manuellement, cela devient le travail de l'intercepteur EJB de JBoss. Vous n'avez
+                    pas non plus à vous occuper des démarcations des transactions dans votre code (sauf
+                    si vous voulez écrire une couche de persistance qui soit portable, dans ce cas vous
+                    pouvez utiliser l'API optionnelle <literal>Transaction</literal> d'Hibernate).
+                    Vous appelez l'<literal>HibernateContext</literal> pour accéder à la <literal>Session</literal>.
+                </para>
+            </listitem>
+            <listitem>
+                <para>
+                    <emphasis>Déploiement HAR :</emphasis> Habituellement vous déployez le service JMX
+                    Hibernate en utilisant le descripteur de déploiement de JBoss (dans un fichier EAR et/ou un SAR),
+                    il supporte toutes les options de configuration usuelles d'une <literal>SessionFactory</literal>
+                    Hibernate. Cependant, vous devez toujours nommer tous vos fichiers de mapping dans le
+                    descripteur de déploiement. Si vous décidez d'utiliser le déploiement optionnel sous forme
+                    de HAR, JBoss détectera automatiquement tous vos fichiers de mapping dans votre fichier HAR.
+                </para>
+            </listitem>
+        </itemizedlist>
+
+        <para>
+            Consultez le guide d'utilisation de JBoss AS pour plus d'informations sur ces options.
+        </para>
+
+        <para>
+            Les statistiques pendant l'exécution d'Hibernate (au runtime) sont une 
+            autre fonctionnalité disponible en tant que service JMX. Voyez pour cela
+            <xref linkend="configuration-optional-statistics"/>.
+        </para>
+    </sect1>
+
+    <sect1 id="architecture-jca" revision="1">
+        <title>Support JCA</title>
+        <para>
+            Hibernate peut aussi être configuré en tant que connecteur JCA. Référez-vous au site
+            web pour de plus amples détails. Il est important de noter que le support JCA d'Hibernate
+            est encore considéré comme expérimental.
+        </para>
+    </sect1>
+    
+    <sect1 id="architecture-current-session" revision="1">
+        <title>Sessions Contextuelles</title>
+        <para>
+            Certaines applications utilisant Hibernate ont besoin d'une sorte de session "contextuelle", où
+            une session est liée à la portée d'un contexte particulier. Cependant, les applications ne définissent
+            pas toutes la notion de contexte de la même manière, et différents contextes définissent différentes
+            portées à la notion de "courant". Les applications à base d'Hibernate, versions précédentes à la 3.0
+            utilisaient généralement un principe maison de sessions contextuelles basées sur le <literal>ThreadLocal</literal>,
+            ainsi que sur des classes utilitaires comme <literal>HibernateUtil</literal>, ou utilisaient des
+            framework tiers (comme Spring ou Pico) qui fournissaient des sessions contextuelles basées sur 
+            l'utilisation de proxy/interception.
+        </para>
+        <para>
+        	A partir de la version 3.0.1, Hibernate a ajouté la méthode <literal>SessionFactory.getCurrentSession()</literal>.
+        	Initialement, cela demandait l'usage de transactions <literal>JTA</literal>, où la
+        	transaction <literal>JTA</literal> définissait la portée et le contexte de la session courante.
+        	L'équipe Hibernate pense que, étant donnée la maturité des implémentations de <literal>JTA TransactionManager</literal> ,
+        	la plupart (sinon toutes) des applications devraient utiliser la gestion des transactions par <literal>JTA</literal> 
+        	qu'elles soient ou non déployées dans un conteneur <literal>J2EE</literal>. Par conséquent,
+        	vous devriez toujours contextualiser vos sessions, si vous en avez besoin, via la méthode basée sur JTA.
+        </para>
+        <para>
+            Cependant, depuis la version 3.1, la logique derrière
+            <literal>SessionFactory.getCurrentSession()</literal> est désormais branchable.  
+            A cette fin, une nouvelle interface d'extension (<literal>org.hibernate.context.CurrentSessionContext</literal>)
+            et un nouveau paramètre de configuration (<literal>hibernate.current_session_context_class</literal>)
+            ont été ajoutés pour permettre de configurer d'autres moyens de définir la portée et le contexte des
+            sessions courantes.
+        </para>
+        <para>
+            Allez voir les Javadocs de l'interface <literal>org.hibernate.context.CurrentSessionContext</literal>
+            pour une description détaillée de son contrat. Elle définit une seule méthode,
+            <literal>currentSession()</literal>, depuis laquelle l'implémentation est responsable
+            de traquer la session courante du contexte. Hibernate fournit deux implémentation 
+            de cette interface.
+        </para>
+
+        <itemizedlist>
+            <listitem>
+                <para>
+                    <literal>org.hibernate.context.JTASessionContext</literal> - les sessions courantes sont
+                    associées à une transaction <literal>JTA</literal>.  La logique est la même que
+                    l'ancienne approche basée sur JTA. Voir les javadocs pour les détails.
+                </para>
+            </listitem>
+            <listitem>
+                <para>
+                    <literal>org.hibernate.context.ThreadLocalSessionContext</literal> - les sessions
+                    courantes sont associées au thread d'exécution. Voir les javadocs pour les détails.
+                </para>
+            </listitem>
+        </itemizedlist>
+
+        <para>
+            Les deux implémentations fournissent un modèle de programmation de type "une session - une transaction
+            à la base de données", aussi connu sous le nom de <emphasis>session-per-request</emphasis>. 
+            Le début et la fin d'une session Hibernate sont définis par la durée d'une transaction de base de données.
+            Si vous utilisez une démarcation programmatique de la transaction (par exemple sous J2SE ou JTA/UserTransaction/BMT),
+            nous vous conseillons d'utiliser l'API Hibernate <literal>Transaction</literal> pour masquer le système
+            de transaction utilisé. Si vous exécutez sous un conteneur EJB qui supporte CMT, vous n'avez besoin d'aucune
+            opérations de démarcations de session ou transaction dans votre code puisque tout
+            est géré de manière déclarative. Référez vous à <xref linkend="transactions"/> pour plus d'informations
+            et des exemples de code.
+        </para>
+
+        <para>
+            Le paramètre de configuration <literal>hibernate.current_session_context_class</literal> 
+            définit quelle implémentation de <literal>org.hibernate.context.CurrentSessionContext</literal> 
+            doit être utilisée. Notez que pour assurer la compatibilité avec les versions précédentes, si
+            ce paramètre n'est pas défini mais qu'un <literal>org.hibernate.transaction.TransactionManagerLookup</literal> 
+            est configuré, Hibernate utilisera le <literal>org.hibernate.context.JTASessionContext</literal>.
+            La valeur de ce paramètre devrait juste nommer la classe d'implémentation à utiliser, 
+            pour les deux implémentations fournies, il y a cependant deux alias correspondant: "jta" et "thread".
+        </para>
+        
+    </sect1>
+
+</chapter>
+

Copied: core/trunk/documentation/manual/fr-FR/src/main/docbook/content/association_mapping.xml (from rev 14070, core/trunk/documentation/manual/fr-FR/src/main/docbook/modules/association_mapping.xml)
===================================================================
--- core/trunk/documentation/manual/fr-FR/src/main/docbook/content/association_mapping.xml	                        (rev 0)
+++ core/trunk/documentation/manual/fr-FR/src/main/docbook/content/association_mapping.xml	2007-10-09 18:28:36 UTC (rev 14074)
@@ -0,0 +1,623 @@
+<?xml version="1.0" encoding="iso-8859-1"?>
+<chapter id="associations">
+
+    <title>Mapper les associations</title>
+
+    <sect1 id="assoc-intro" revision="1">
+        <title>Introduction</title>
+        
+        <para>
+            Correctement mapper les associations est souvent la tâche la plus difficile.
+            Dans cette section nous traiterons les cas classiques les uns après les autres.
+            Nous commencerons d'abbord par les mappings unidirectionnels, puis nous aborderons
+            la question des mappings bidirectionnels. Nous illustrerons tous nos exemples 
+            avec les classes <literal>Person</literal> et <literal>Address</literal>.
+        </para>
+        
+        <para>
+        	Nous utiliserons deux critères pour classer les associations : le premier 
+        	sera de savoir si l'association est bâti sur une table supplémentaire d'association
+        	et le deuxieme sera basé sur la multiplicité de cette association.
+        </para>
+        
+        <para>
+        	Autoriser une clé étrangère nulle est considéré comme un mauvais choix dans 
+        	la construction d'un modèle de données. Nous supposerons donc que dans tous 
+        	les exemples qui vont suivre on aura interdit la valeur nulle pour les clés 
+        	étrangères. Attention, ceci ne veut pas dire que Hibernate ne supporte pas 
+        	les clés étrangères pouvant prendre des valeurs nulles, les exemples qui suivent 
+        	continueront de fonctionner si vous décidiez ne plus imposer la contrainte 
+        	de non-nullité sur les clés étrangères.
+        </para>
+        
+    </sect1>
+
+    <sect1 id="assoc-unidirectional" revision="1">
+        <title>Association unidirectionnelle</title>
+        
+        <sect2 id="assoc-unidirectional-m21" >
+        <title>plusieurs à un</title>
+        
+        <para>
+            Une <emphasis>association plusieurs-à-un (many-to-one) unidirectionnelle </emphasis> 
+            est le type que l'on rencontre le plus souvent dans les associations unidirectionnelles.
+        </para>
+        
+        <programlisting><![CDATA[<class name="Person">
+    <id name="id" column="personId">
+        <generator class="native"/>
+    </id>
+    <many-to-one name="address" 
+        column="addressId"
+        not-null="true"/>
+</class>
+
+<class name="Address">
+    <id name="id" column="addressId">
+        <generator class="native"/>
+    </id>
+</class>]]></programlisting>
+        <programlisting><![CDATA[
+create table Person ( personId bigint not null primary key, addressId bigint not null )
+create table Address ( addressId bigint not null primary key )
+        ]]></programlisting>
+
+        
+        </sect2>
+
+        <sect2 id="assoc-unidirectional-121">
+        <title>un à un</title>
+        
+        <para>
+            une <emphasis>association un-à-un (one-to-one) sur une clé étrangère</emphasis>
+            est presque identique. La seule différence est sur la contrainte d'unicité que
+            l'on impose à cette colonne.
+        </para>
+        
+       <programlisting><![CDATA[<class name="Person">
+    <id name="id" column="personId">
+        <generator class="native"/>
+    </id>
+    <many-to-one name="address" 
+        column="addressId" 
+        unique="true"
+        not-null="true"/>
+</class>
+
+<class name="Address">
+    <id name="id" column="addressId">
+        <generator class="native"/>
+    </id>
+</class>]]></programlisting>
+        <programlisting><![CDATA[
+create table Person ( personId bigint not null primary key, addressId bigint not null unique )
+create table Address ( addressId bigint not null primary key )
+        ]]></programlisting>
+        
+        <para>
+            Une <emphasis>association un-à-un (one-to-one) unidirectionnelle sur une clé primaire</emphasis>
+            utilise un générateur d'identifiant particulier. (Remarquez que nous avons inversé le sens de cette
+            association dans cet exemple.)
+        </para>
+        
+       <programlisting><![CDATA[<class name="Person">
+    <id name="id" column="personId">
+        <generator class="native"/>
+    </id>
+</class>
+
+<class name="Address">
+    <id name="id" column="personId">
+        <generator class="foreign">
+            <param name="property">person</param>
+        </generator>
+    </id>
+    <one-to-one name="person" constrained="true"/>
+</class>]]></programlisting>
+        <programlisting><![CDATA[
+create table Person ( personId bigint not null primary key )
+create table Address ( personId bigint not null primary key )
+        ]]></programlisting>
+        
+        </sect2>
+        
+        <sect2 id="assoc-unidirectional-12m">
+        <title>un à plusieurs</title>
+        
+        <para>
+            Une <emphasis>association un-à-plusieurs (one-to-many) unidirectionnelle sur une 
+            clé étrangère</emphasis> est vraiment inhabituelle, et n'est pas vraiment recommandée.
+        </para>
+        
+        <programlisting><![CDATA[<class name="Person">
+    <id name="id" column="personId">
+        <generator class="native"/>
+    </id>
+    <set name="addresses">
+        <key column="personId" 
+            not-null="true"/>
+        <one-to-many class="Address"/>
+    </set>
+</class>
+
+<class name="Address">
+    <id name="id" column="addressId">
+        <generator class="native"/>
+    </id>
+</class>]]></programlisting>
+        <programlisting><![CDATA[
+create table Person ( personId bigint not null primary key )
+create table Address ( addressId bigint not null primary key, personId bigint not null )
+        ]]></programlisting>
+        
+        <para>
+            Nous pensons qu'il est préférable d'utiliser une table de jointure pour ce type d'association.
+        </para>
+        
+        </sect2>
+    
+    </sect1>
+
+    <sect1 id="assoc-unidirectional-join" revision="1">
+        <title>Associations unidirectionnelles avec tables de jointure</title>
+        
+        <sect2 id="assoc-unidirectional-join-12m">
+        <title>un à plusieurs</title>
+        
+        <para>
+            Une <emphasis>association unidirectionnelle un-à-plusieurs (one-to-many) avec
+            une table de jointure</emphasis> est un bien meilleur choix. 
+            Remarquez qu'en spécifiant <literal>unique="true"</literal>,
+            on a changé la multiplicité plusieurs-à-plusieurs (many-to-many) pour 
+            un-à-plusieurs (one-to-many).
+        </para>
+        
+        <programlisting><![CDATA[<class name="Person">
+    <id name="id" column="personId">
+        <generator class="native"/>
+    </id>
+    <set name="addresses" table="PersonAddress">
+        <key column="personId"/>
+        <many-to-many column="addressId"
+            unique="true"
+            class="Address"/>
+    </set>
+</class>
+
+<class name="Address">
+    <id name="id" column="addressId">
+        <generator class="native"/>
+    </id>
+</class>]]></programlisting>
+        <programlisting><![CDATA[
+create table Person ( personId bigint not null primary key )
+create table PersonAddress ( personId not null, addressId bigint not null primary key )
+create table Address ( addressId bigint not null primary key )
+        ]]></programlisting>
+        
+        </sect2>
+
+        <sect2 id="assoc-unidirectional-join-m21">
+        <title>plusieurs à un</title>
+        
+        <para>
+            Une <emphasis>assiociation plusieurs-à-un (many-to-one) unidirectionnelle sur
+            une table de jointure</emphasis> est très fréquente quand l'association est optionnelle.
+        </para>
+        
+        <programlisting><![CDATA[<class name="Person">
+    <id name="id" column="personId">
+        <generator class="native"/>
+    </id>
+    <join table="PersonAddress" 
+        optional="true">
+        <key column="personId" unique="true"/>
+        <many-to-one name="address"
+            column="addressId" 
+            not-null="true"/>
+    </join>
+</class>
+
+<class name="Address">
+    <id name="id" column="addressId">
+        <generator class="native"/>
+    </id>
+</class>]]></programlisting>
+        <programlisting><![CDATA[
+create table Person ( personId bigint not null primary key )
+create table PersonAddress ( personId bigint not null primary key, addressId bigint not null )
+create table Address ( addressId bigint not null primary key )
+        ]]></programlisting>
+        
+        </sect2>
+
+        <sect2 id="assoc-unidirectional-join-121">
+        <title>un à un</title>
+        
+        <para>
+            Une <emphasis>association unidirectionnelle un-à-un (one-to-one) sur une table
+            de jointure</emphasis> est extrèmement rare mais envisageable.
+        </para>
+        
+        <programlisting><![CDATA[<class name="Person">
+    <id name="id" column="personId">
+        <generator class="native"/>
+    </id>
+    <join table="PersonAddress" 
+        optional="true">
+        <key column="personId" 
+            unique="true"/>
+        <many-to-one name="address"
+            column="addressId" 
+            not-null="true"
+            unique="true"/>
+    </join>
+</class>
+
+<class name="Address">
+    <id name="id" column="addressId">
+        <generator class="native"/>
+    </id>
+</class>]]></programlisting>
+        <programlisting><![CDATA[
+create table Person ( personId bigint not null primary key )
+create table PersonAddress ( personId bigint not null primary key, addressId bigint not null unique )
+create table Address ( addressId bigint not null primary key )
+        ]]></programlisting>
+        
+        </sect2>
+
+        <sect2 id="assoc-unidirectional-join-m2m">
+        <title>plusieurs à plusieurs</title>
+        
+        <para>
+            Finallement, nous avons <emphasis>l'association unidirectionnelle plusieurs-à-plusieurs (many-to-many)</emphasis>.
+        </para>
+        
+        <programlisting><![CDATA[<class name="Person">
+    <id name="id" column="personId">
+        <generator class="native"/>
+    </id>
+    <set name="addresses" table="PersonAddress">
+        <key column="personId"/>
+        <many-to-many column="addressId"
+            class="Address"/>
+    </set>
+</class>
+
+<class name="Address">
+    <id name="id" column="addressId">
+        <generator class="native"/>
+    </id>
+</class>]]></programlisting>
+        <programlisting><![CDATA[
+create table Person ( personId bigint not null primary key )
+create table PersonAddress ( personId bigint not null, addressId bigint not null, primary key (personId, addressId) )
+create table Address ( addressId bigint not null primary key )
+        ]]></programlisting>
+        
+        </sect2>
+
+    </sect1>
+
+    <sect1 id="assoc-bidirectional" revision="1">
+        <title>Associations bidirectionnelles</title>
+        
+        <sect2 id="assoc-bidirectional-m21" revision="2">
+        <title>un à plusieurs / plusieurs à un</title>
+        
+        <para>
+            Une <emphasis>association bidirectionnelle plusieurs à un (many-to-one)</emphasis>  
+            est le type d'association que l'on rencontre le plus souvent. (c'est la façon standard de créer
+            des relations parents/enfants.)
+        </para>
+        
+        <programlisting><![CDATA[<class name="Person">
+    <id name="id" column="personId">
+        <generator class="native"/>
+    </id>
+    <many-to-one name="address" 
+        column="addressId"
+        not-null="true"/>
+</class>
+
+<class name="Address">
+    <id name="id" column="addressId">
+        <generator class="native"/>
+    </id>
+    <set name="people" inverse="true">
+        <key column="addressId"/>
+        <one-to-many class="Person"/>
+    </set>
+</class>]]></programlisting>
+
+        <programlisting><![CDATA[
+create table Person ( personId bigint not null primary key, addressId bigint not null )
+create table Address ( addressId bigint not null primary key )
+        ]]></programlisting>
+        
+        <para>
+            Si vous utilisez une <literal>List</literal> (ou toute autre collection indexée) vous devez
+            paramétrer la colonne <literal>key</literal> de la clé étrangère à <literal>not null</literal>,
+            et laisser Hibernate gérer l'association depuis l'extrémité collection pour maintenir l'index
+            de chaque élément (rendant l'autre extrémité virtuellement inverse en paramétrant
+            <literal>update="false"</literal> et <literal>insert="false"</literal>):
+        </para>
+
+        <programlisting><![CDATA[<class name="Person">
+   <id name="id"/>
+   ...
+   <many-to-one name="address"
+      column="addressId"
+      not-null="true"
+      insert="false"
+      update="false"/>
+</class>
+
+<class name="Address">
+   <id name="id"/>
+   ...
+   <list name="people">
+      <key column="addressId" not-null="true"/>
+      <list-index column="peopleIdx"/>
+      <one-to-many class="Person"/>
+   </list>
+</class>]]></programlisting>
+        
+        </sect2>
+        
+        <sect2 id="assoc-bidirectional-121">
+        <title>Un à un</title>
+        
+        <para>
+            Une <emphasis>association bidirectionnelle un à un (one-to-one) sur une clé étrangère</emphasis>
+            est aussi très fréquente.
+        </para>
+        
+       <programlisting><![CDATA[<class name="Person">
+    <id name="id" column="personId">
+        <generator class="native"/>
+    </id>
+    <many-to-one name="address" 
+        column="addressId" 
+        unique="true"
+        not-null="true"/>
+</class>
+
+<class name="Address">
+    <id name="id" column="addressId">
+        <generator class="native"/>
+    </id>
+   <one-to-one name="person" 
+        property-ref="address"/>
+</class>]]></programlisting>
+        <programlisting><![CDATA[
+create table Person ( personId bigint not null primary key, addressId bigint not null unique )
+create table Address ( addressId bigint not null primary key )
+        ]]></programlisting>
+        
+        <para>
+            Une <emphasis>association bidirectionnelle un-à-un (one-to-one) sur une clé primaire</emphasis>
+            utilise un générateur particulier d'id.
+        </para>
+        
+       <programlisting><![CDATA[<class name="Person">
+    <id name="id" column="personId">
+        <generator class="native"/>
+    </id>
+    <one-to-one name="address"/>
+</class>
+
+<class name="Address">
+    <id name="id" column="personId">
+        <generator class="foreign">
+            <param name="property">person</param>
+        </generator>
+    </id>
+    <one-to-one name="person" 
+        constrained="true"/>
+</class>]]></programlisting>
+        <programlisting><![CDATA[
+create table Person ( personId bigint not null primary key )
+create table Address ( personId bigint not null primary key )
+        ]]></programlisting>
+        
+        </sect2>
+        
+    </sect1>
+
+    <sect1 id="assoc-bidirectional-join" revision="1">
+        <title>Associations bidirectionnelles avec table de jointure</title>
+        
+        <sect2 id="assoc-bidirectional-join-12m">
+        <title>un à plusieurs / plusieurs à un</title>
+        
+        <para>
+            Une <emphasis>association bidirectionnelle un-à-plusieurs (one-to-many) sur une table de jointure </emphasis>.
+            Remarquez que <literal>inverse="true"</literal> peut s'appliquer sur les deux extrémités de l'
+            association, sur la collection, ou sur la jointure.
+        </para>
+        
+        <programlisting><![CDATA[<class name="Person">
+    <id name="id" column="personId">
+        <generator class="native"/>
+    </id>
+    <set name="addresses" 
+        table="PersonAddress">
+        <key column="personId"/>
+        <many-to-many column="addressId"
+            unique="true"
+            class="Address"/>
+    </set>
+</class>
+
+<class name="Address">
+    <id name="id" column="addressId">
+        <generator class="native"/>
+    </id>
+    <join table="PersonAddress" 
+        inverse="true" 
+        optional="true">
+        <key column="addressId"/>
+        <many-to-one name="person"
+            column="personId"
+            not-null="true"/>
+    </join>
+</class>]]></programlisting>
+        <programlisting><![CDATA[
+create table Person ( personId bigint not null primary key )
+create table PersonAddress ( personId bigint not null, addressId bigint not null primary key )
+create table Address ( addressId bigint not null primary key )
+        ]]></programlisting>
+        
+        </sect2>
+
+         <sect2 id="assoc-bidirectional-join-121">
+        <title>Un à un</title>
+        
+        <para>
+            Une <emphasis>association bidirectionnelle un-à-un (one-to-one) sur une table de jointure</emphasis> 
+            est extrèmement rare mais envisageable.
+        </para>
+        
+        <programlisting><![CDATA[<class name="Person">
+    <id name="id" column="personId">
+        <generator class="native"/>
+    </id>
+    <join table="PersonAddress" 
+        optional="true">
+        <key column="personId" 
+            unique="true"/>
+        <many-to-one name="address"
+            column="addressId" 
+            not-null="true"
+            unique="true"/>
+    </join>
+</class>
+
+<class name="Address">
+    <id name="id" column="addressId">
+        <generator class="native"/>
+    </id>
+    <join table="PersonAddress" 
+        optional="true"
+        inverse="true">
+        <key column="addressId" 
+            unique="true"/>
+        <many-to-one name="person"
+            column="personId" 
+            not-null="true"
+            unique="true"/>
+    </join>
+</class>]]></programlisting>
+        <programlisting><![CDATA[
+create table Person ( personId bigint not null primary key )
+create table PersonAddress ( personId bigint not null primary key, addressId bigint not null unique )
+create table Address ( addressId bigint not null primary key )
+        ]]></programlisting>
+
+        </sect2>
+        
+        <sect2 id="assoc-bidirectional-join-m2m" revision="1">
+        <title>plusieurs à plusieurs</title>
+        
+        <para>
+            Finallement nous avons <emphasis>l'association bidirectionnelle plusieurs à plusieurs</emphasis>.
+        </para>
+        
+        <programlisting><![CDATA[<class name="Person">
+    <id name="id" column="personId">
+        <generator class="native"/>
+    </id>
+    <set name="addresses" table="PersonAddress">
+        <key column="personId"/>
+        <many-to-many column="addressId"
+            class="Address"/>
+    </set>
+</class>
+
+<class name="Address">
+    <id name="id" column="addressId">
+        <generator class="native"/>
+    </id>
+    <set name="people" inverse="true"  table="PersonAddress">
+        <key column="addressId"/>
+        <many-to-many column="personId"
+            class="Person"/>
+    </set>
+</class>]]></programlisting>
+
+        <programlisting><![CDATA[
+create table Person ( personId bigint not null primary key )
+create table PersonAddress ( personId bigint not null, addressId bigint not null, primary key (personId, addressId) )
+create table Address ( addressId bigint not null primary key )
+        ]]></programlisting>
+        
+        </sect2>
+        
+    </sect1>
+    
+    <sect1 id="assoc-complex">
+        <title>Des mappings plus complexes</title>
+        
+        <para>
+            Des associations encore plus complexes sont <emphasis>extrêmement</emphasis> rares. 
+            Hibernate permet de gérer des situations plus complexes en utilisant des
+            parties SQL dans les fichiers de mapping. Par exemple, si une table
+            avec l'historiques des informations d'un compte définit les colonnes
+            <literal>accountNumber</literal>, <literal>effectiveEndDate</literal> 
+            et <literal>effectiveStartDate</literal>, mappées de telle sorte:
+        </para>
+        
+        <programlisting><![CDATA[<properties name="currentAccountKey">
+    <property name="accountNumber" type="string" not-null="true"/>
+    <property name="currentAccount" type="boolean">
+        <formula>case when effectiveEndDate is null then 1 else 0 end</formula>
+    </property>
+</properties>
+<property name="effectiveEndDate" type="date"/>
+<property name="effectiveStateDate" type="date" not-null="true"/>]]></programlisting>
+
+        <para>
+            alors nous pouvons mapper une association à l'instance <emphasis>courante</emphasis>  
+            (celle avec une <literal>effectiveEndDate</literal>) nulle en utilisant:
+        </para>
+        
+        <programlisting><![CDATA[<many-to-one name="currentAccountInfo" 
+        property-ref="currentAccountKey"
+        class="AccountInfo">
+    <column name="accountNumber"/>
+    <formula>'1'</formula>
+</many-to-one>]]></programlisting>
+
+        <para>
+            Dans un exemple plus complexe, imaginez qu'une association entre
+            <literal>Employee</literal> et <literal>Organization</literal> est gérée
+            dans une table <literal>Employment</literal> pleines de données historiques.
+            Dans ce cas, une association vers l'employeur <emphasis>le plus récent</emphasis>
+            (celui avec la <literal>startDate</literal> la plus récente) pourrait être mappée comme cela:
+        </para>
+        
+        <programlisting><![CDATA[<join>
+    <key column="employeeId"/>
+    <subselect>
+        select employeeId, orgId 
+        from Employments 
+        group by orgId 
+        having startDate = max(startDate)
+    </subselect>
+    <many-to-one name="mostRecentEmployer" 
+            class="Organization" 
+            column="orgId"/>
+</join>]]></programlisting>
+
+        <para>
+            Vous pouvez être créatif grace à ces possibilités, mais il est généralement plus pratique
+            d'utiliser des requêtes HQL ou criteria dans ce genre de situation.
+        </para>
+
+    </sect1>
+
+
+</chapter>
+

Copied: core/trunk/documentation/manual/fr-FR/src/main/docbook/content/basic_mapping.xml (from rev 14070, core/trunk/documentation/manual/fr-FR/src/main/docbook/modules/basic_mapping.xml)
===================================================================
--- core/trunk/documentation/manual/fr-FR/src/main/docbook/content/basic_mapping.xml	                        (rev 0)
+++ core/trunk/documentation/manual/fr-FR/src/main/docbook/content/basic_mapping.xml	2007-10-09 18:28:36 UTC (rev 14074)
@@ -0,0 +1,3117 @@
+<?xml version='1.0' encoding="iso-8859-1"?>
+<chapter id="mapping">
+    <title>Mapping O/R basique</title>
+    <sect1 id="mapping-declaration" revision="1">
+        <title>Déclaration de Mapping</title>
+        <para>
+            Les mappings Objet/relationnel sont généralement définis dans un document XML. 
+            Le document de mapping est conçu pour être lisible et éditable à la main. 
+            Le langage de mapping est Java-centrique, c'est à dire que les mappings sont construits 
+            à partir des déclarations des classes persistantes et non des déclarations des tables.
+        </para>
+        <para>
+            Remarquez que même si beaucoup d'utilisateurs de Hibernate préfèrent écrire les 
+            fichiers de mappings à la main, plusieurs outils existent pour générer ce document, 
+            notamment XDoclet, Middlegen et AndroMDA.
+        </para>
+        <para>Démarrons avec un exemple de mapping :</para>
+        <programlisting id="mapping-declaration-ex1" revision="1"><![CDATA[<?xml version="1.0"?>
+<!DOCTYPE hibernate-mapping PUBLIC
+      "-//Hibernate/Hibernate Mapping DTD 3.0//EN"
+          "http://hibernate.sourceforge.net/hibernate-mapping-3.0.dtd">
+
+<hibernate-mapping package="eg">
+
+        <class name="Cat" 
+            table="cats"
+            discriminator-value="C">
+                
+                <id name="id">
+                        <generator class="native"/>
+                </id>
+
+                <discriminator column="subclass" 
+                     type="character"/>
+
+                <property name="weight"/>
+
+                <property name="birthdate"
+                    type="date" 
+                    not-null="true" 
+                    update="false"/>
+
+                <property name="color"
+                    type="eg.types.ColorUserType"
+                    not-null="true"
+                    update="false"/>
+
+                <property name="sex"
+                    not-null="true" 
+                    update="false"/>
+
+                <property name="litterId"
+                    column="litterId"
+                    update="false"/>
+
+                <many-to-one name="mother"
+                    column="mother_id"
+                    update="false"/>
+
+                <set name="kittens"
+                    inverse="true"
+                    order-by="litter_id">
+                        <key column="mother_id"/>
+                        <one-to-many class="Cat"/>
+                </set>
+
+                <subclass name="DomesticCat"
+                    discriminator-value="D">
+
+                        <property name="name" 
+                            type="string"/>
+
+                </subclass>
+
+        </class>
+
+        <class name="Dog">
+                <!-- mapping for Dog could go here -->
+        </class>
+
+</hibernate-mapping>]]></programlisting>
+        <para>
+             Etudions le contenu du document de mapping. Nous décrirons uniquement 
+             les éléments et attributs du document utilisés par Hibernate à l'exécution. 
+             Le document de mapping contient aussi des attributs et éléments optionnels 
+             qui agissent sur le schéma de base de données exporté par l'outil de 
+             génération de schéma. (Par exemple l'attribut <literal>not-null</literal>.)
+        </para>
+        <sect2 id="mapping-declaration-doctype" revision="2">
+            <title>Doctype</title>
+            <para>
+                Tous les mappings XML devraient utiliser le doctype indiqué. 
+                Ce fichier est présent à l'URL ci-dessus, dans le répertoire 
+                <literal>hibernate-x.x.x/src/org/hibernate</literal> ou dans <literal>hibernate3.jar</literal>. 
+                Hibernate va toujours chercher la DTD dans son classpath en premier lieu. Si vous constatez 
+                des recherches de la DTD sur Internet, vérifiez votre déclaration de DTD par rapport 
+                au contenu de votre classpath.
+            </para>
+        </sect2>
+        <sect2 id="mapping-declaration-mapping" revision="3">
+            <title>hibernate-mapping</title>
+            <para>
+                Cet élément a plusieurs attributs optionnels. Les attributs <literal>schema</literal> et <literal>catalog</literal> 
+                indiquent que les tables référencées par ce mapping appartiennent au schéma nommé et/ou au catalogue. 
+                S'ils sont spécifiés, les noms de tables seront qualifiés par les noms de schéma et catalogue. 
+                L'attribut <literal>default-cascade</literal> indique quel type de cascade sera utlisé par défaut 
+                pour les propriétés et collections qui ne précisent pas l'attribut <literal>cascade</literal>. 
+                L'attribut <literal>auto-import</literal> nous permet d'utiliser par défaut des noms de classes 
+                non qualifiés dans le langage de requête.
+            </para>
+            <programlistingco>
+                <areaspec>
+                    <area id="hm1" coords="2 55"/>
+                    <area id="hm2" coords="3 55"/>
+                    <area id="hm3" coords="4 55"/>
+                    <area id="hm4" coords="5 55"/>
+                    <area id="hm5" coords="6 55"/>
+                    <area id="hm6" coords="7 55"/>
+                    <area id="hm7" coords="8 55"/>
+                </areaspec>
+                <programlisting><![CDATA[<hibernate-mapping
+         schema="schemaName"
+         catalog="catalogName"
+         default-cascade="cascade_style"
+         default-access="field|property|ClassName"
+         default-lazy="true|false"
+         auto-import="true|false"
+         package="package.name"
+ />]]></programlisting>
+                <calloutlist>
+                    <callout arearefs="hm1">
+                        <para>
+                            <literal>schema</literal> (optionnel) : Le nom d'un schéma de base de données.
+                         </para>
+                    </callout>
+                    <callout arearefs="hm2">
+                        <para>
+                            <literal>catalog</literal> (optionnel) : Le nom d'un catalogue de base de données.
+                         </para>
+                    </callout>
+                    <callout arearefs="hm3">
+                        <para>
+                            <literal>default-cascade</literal> (optionnel - par défaut vaut :  <literal>none</literal>) : 
+                             Un type de cascade par défaut.
+                         </para>
+                    </callout>
+                    <callout arearefs="hm4">
+                        <para>
+                            <literal>default-access</literal> (optionnel - par défaut vaut : <literal>property</literal>) :
+                            Comment hibernate accèdera aux propriétés. On peut aussi 
+                            redéfinir sa propre implémentation de <literal>PropertyAccessor</literal>.
+                         </para>
+                    </callout>
+                    <callout arearefs="hm5">
+                        <para>
+                            <literal>default-lazy</literal> (optionnel - par défaut vaut : <literal>true</literal>) :
+                             Valeur par défaut pour un attribut <literal>lazy</literal> 
+                             non spécifié : celui des mappings de classes et de collection.
+                         </para>
+                    </callout>
+                    <callout arearefs="hm6">
+                        <para>
+                            <literal>auto-import</literal> (optionnel - par défaut vaut : <literal>true</literal>) :
+                             Spécifie si l'on peut utiliser des noms de classes 
+                             non qualifiés (des classes de ce mapping) dans le langage de requête.
+                         </para>
+                    </callout>
+                    <callout arearefs="hm7">
+                        <para>
+                            <literal>package</literal> (optionnel) : Préfixe de package par défaut pour 
+                            les noms de classe non qualifiés du document de mapping.
+                             
+                         </para>
+                    </callout>
+                </calloutlist>
+            </programlistingco>
+            <para>
+                 Si deux classes possèdent le même nom de classe (non qualifié), vous devez indiquer 
+                 <literal>auto-import="false"</literal>. Hibernate lancera une exception 
+                 si vous essayez d'assigner à deux classes le même nom importé.
+             </para>
+            <para>
+                 Notez que l'élément <literal>hibernate-mapping</literal> vous permet d'imbriquer plusieurs mappings de
+                 <literal>&lt;class&gt;</literal> persistantes, comme dans l'exemple ci-dessus.
+                 Cependant la bonne pratique (ce qui est attendu par certains outils) est 
+                 de mapper une seule classe (ou une seule hiérarchie de classes)
+                 par fichier de mapping et de nommer ce fichier d'après le nom de la superclasse, par exemple
+                 <literal>Cat.hbm.xml</literal>, <literal>Dog.hbm.xml</literal>, ou en cas d'héritage,
+                 <literal>Animal.hbm.xml</literal>.
+             </para>
+        </sect2>
+        <sect2 id="mapping-declaration-class" revision="3">
+            <title>class</title>
+            <para>
+                Déclarez une classe persistante avec l'élément <literal>class</literal> :
+            </para>
+            <programlistingco>
+                <areaspec>
+                    <area id="class1" coords="2 55"/>
+                    <area id="class2" coords="3 55"/>
+                    <area id="class3" coords="4 55"/>
+                    <area id="class4" coords="5 55"/>
+                    <area id="class5" coords="6 55"/>
+                    <area id="class6" coords="7 55"/>
+                    <area id="class7" coords="8 55"/>
+                    <area id="class8" coords="9 55"/>
+                    <area id="class9" coords="10 55"/>
+                    <area id="class10" coords="11 55"/>
+                    <area id="class11" coords="12 55"/>
+                    <area id="class12" coords="13 55"/>
+                    <area id="class13" coords="14 55"/>
+                    <area id="class14" coords="15 55"/>
+                    <area id="class15" coords="16 55"/>
+                    <area id="class16" coords="17 55"/>
+                    <area id="class17" coords="18 55"/>
+                    <area id="class18" coords="19 55"/>
+                    <area id="class19" coords="20 55"/>
+                    <area id="class20" coords="21 55"/>
+                    <area id="class21" coords="22 55"/>
+                </areaspec>
+                <programlisting><![CDATA[<class
+        name="ClassName"
+        table="tableName"
+        discriminator-value="discriminator_value"
+        mutable="true|false"
+        schema="owner"
+        catalog="catalog"
+        proxy="ProxyInterface"
+        dynamic-update="true|false"
+        dynamic-insert="true|false"
+        select-before-update="true|false"
+        polymorphism="implicit|explicit"
+        where="arbitrary sql where condition"
+        persister="PersisterClass"
+        batch-size="N"
+        optimistic-lock="none|version|dirty|all"
+        lazy="true|false"
+        entity-name="EntityName"
+        catalog="catalog"
+        check="arbitrary sql check condition"
+        rowid="rowid"
+        subselect="SQL expression"
+        abstract="true|false"
+        entity-name="EntityName"
+/>]]></programlisting>
+                <calloutlist>
+                    <callout arearefs="class1">
+                        <para>
+                            <literal>name</literal> (optionnel) : Le nom Java complet de la classe (ou interface) persistante.
+                             Si cet attribut est absent, il est supposé que ce mapping ne se rapporte pas à une entité POJO.
+                        </para>
+                    </callout>
+                    <callout arearefs="class2">
+                        <para>
+                            <literal>table</literal> (optionnel - par défaut le nom (non-qualifié) de la classe) :  Le 
+                            nom de sa table en base de données.
+                        </para>
+                    </callout>
+                    <callout arearefs="class3">
+                        <para>
+                            <literal>discriminator-value</literal> (optionnel - par défaut le nom de la classe) : 
+                            Une valeur permettant de distinguer les sous-classes dans le cas de l'utilisation du polymorphisme. 
+                            Les valeurs <literal>null</literal> et <literal>not null</literal> sont autorisées.
+                        </para>
+                    </callout>
+                    <callout arearefs="class4">
+                        <para>
+                            <literal>mutable</literal> (optionnel, vaut <literal>true</literal> par défaut) : Spécifie 
+                            que des instances de la classe sont (ou non) immuables.
+                        </para>
+                    </callout>
+                    <callout arearefs="class5">
+                        <para>
+                            <literal>schema</literal> (optionnel) : Surcharge le nom de schéma spécifié par 
+                            l'élément racine <literal>&lt;hibernate-mapping&gt;</literal>.
+                        </para>
+                    </callout>
+                    <callout arearefs="class6">
+                        <para>
+                            <literal>catalog</literal> (optionnel) : Surcharge le nom du catalogue spécifié par
+                            l'élément racine <literal>&lt;hibernate-mapping&gt;</literal>.
+                        </para>
+                    </callout>
+                    <callout arearefs="class7">
+                        <para>
+                            <literal>proxy</literal> (optionnel) : Spécifie une interface à utiliser pour l'initialisation différée (lazy loading)
+                            des proxies. Vous pouvez indiquer le nom de la classe elle-même.
+                        </para>
+                    </callout>
+                    <callout arearefs="class8">
+                        <para>
+                            <literal>dynamic-update</literal> (optionnel, par défaut à <literal>false</literal>) : 
+                            Spécifie que les  <literal>UPDATE</literal> SQL doivent être générés à l'exécution et contenir 
+                            uniquement les colonnes dont les valeurs ont été modifiées.
+                        </para>
+                    </callout>
+                    <callout arearefs="class9">
+                        <para>
+                            <literal>dynamic-insert</literal> (optionnel, par défaut à <literal>false</literal>): 
+                            Spécifie que les <literal>INSERT</literal> SQL doivent être générés à l'exécution et ne contenir 
+                            que les colonnes dont les valeurs sont non nulles.
+                        </para>
+                    </callout>
+                    <callout arearefs="class10">
+                        <para>
+                            <literal>select-before-update</literal> (optionnel, par défaut à <literal>false</literal>): 
+                            Spécifie que Hibernate ne doit <emphasis>jamais</emphasis> exécuter un <literal>UPDATE</literal> SQL 
+                            sans être certain qu'un objet a été réellement modifié. Dans certains cas, (en réalité, seulement 
+                            quand un objet transient a été associé à une nouvelle session par <literal>update()</literal>), 
+                            cela signifie que Hibernate exécutera un <literal>SELECT</literal> SQL pour s'assurer qu'un 
+                            <literal>UPDATE</literal> SQL est véritablement nécessaire.
+                        </para>
+                    </callout>
+                    <callout arearefs="class11">
+                        <para>
+                            <literal>polymorphism</literal> (optionnel, vaut <literal>implicit</literal> par défaut) : 
+                            Détermine si, pour cette classe, une requête polymorphique implicite ou explicite est utilisée.
+                        </para>
+                    </callout>
+                    <callout arearefs="class12">
+                        <para>
+                            <literal>where</literal> (optionnel) spécifie une clause SQL <literal>WHERE</literal> 
+                            à utiliser lorsque l'on récupère des objets de cette classe.
+                        </para>
+                    </callout>
+                    <callout arearefs="class13">
+                        <para>
+                            <literal>persister</literal> (optionnel) : Spécifie un <literal>ClassPersister</literal> particulier.
+                        </para>
+                    </callout>
+                    <callout arearefs="class14">
+                        <para>
+                            <literal>batch-size</literal> (optionnel, par défaut = <literal>1</literal>) : spécifie une taille de batch 
+                            pour remplir les instances de cette classe par identifiant en une seule requête.
+                        </para>
+                    </callout>
+                    <callout arearefs="class15">
+                        <para>
+                            <literal>optimistic-lock</literal> (optionnel, par défaut = <literal>version</literal>) : 
+                            Détermine la stratégie de verrou optimiste.
+                        </para>
+                    </callout>
+                    <callout arearefs="class16">
+                        <para>
+                            <literal>lazy</literal> (optionnel) : Déclarer <literal>lazy="true"</literal> est un raccourci
+                            pour spécifier le nom de la classe comme étant l'interface <literal>proxy</literal>.
+                        </para>
+                    </callout>
+                    <callout arearefs="class17">
+                        <para>
+                            <literal>entity-name</literal> (optionnel) : Hibernate3 permet à une classe d'être
+                            mappée plusieurs fois (potentiellement à plusieurs tables), et permet aux mappings d'entité d'être
+                            représentés par des Maps ou du XML au niveau Java. Dans ces cas, vous devez indiquer un nom explicite arbitraire pour
+                            les entités. Voir <xref linkend="persistent-classes-dynamicmodels"/> et <xref linkend="xml"/>
+                            pour plus d'informations.
+                        </para>
+                    </callout>
+                    <callout arearefs="class18">
+                        <para>
+                            <literal>catalog</literal> (optionnel) : The name of a database catalog used for this
+                            class and its table.
+                        </para>
+                    </callout>
+                    <callout arearefs="class19">
+                        <para>
+                            <literal>check</literal> (optionnel) : expression SQL utilisée pour générer une contrainte 
+                            de vérification multi-lignes pour la génération automatique de schéma.
+                        </para>
+                    </callout>
+                    <callout arearefs="class20">
+                        <para>
+                            <literal>rowid</literal> (optionnel) : Hibernate peut utiliser des ROWID sur les bases de
+                            données qui utilisent ce mécanisme. Par exemple avec Oracle, Hibernate peut utiliser la colonne additionnelle 
+                            <literal>rowid</literal> pour des mises à jour rapides si cette option vaut  <literal>rowid</literal>. Un ROWID représente
+                            la localisation physique d'un tuple enregistré.
+                        </para>
+                    </callout>
+                    <callout arearefs="class21">
+                        <para>
+                            <literal>subselect</literal> (optionnel) : Permet de mapper une entité immuable en lecture-seule 
+                            sur un sous-select de base de données. Utile pour avoir une vue au lieu d'une table en base, mais à éviter. Voir plus bas 
+                            pour plus d'information.
+                        </para>
+                    </callout>
+                    <callout arearefs="class22">
+                        <para>
+                            <literal>abstract</literal> (optionnel) : Utilisé pour marquer des superclasses abstraites dans 
+                            des hiérarchies de <literal>&lt;union-subclass&gt;</literal>.
+                        </para>
+                    </callout>
+                </calloutlist>
+            </programlistingco>
+            <para>
+                Il est tout à fait possible d'utiliser une interface comme nom 
+                de classe persistante. Vous devez alors déclarer les classes implémentant
+                cette interface en utilisant l'élément <literal>&lt;subclass&gt;</literal>. 
+                Vous pouvez faire persister toute classe interne <emphasis>static</emphasis>. 
+                Vous devez alors spécifier le nom de la classe par la notation habituelle 
+                des classes internes c'est à dire <literal>eg.Foo$Bar</literal>.
+            </para>
+            <para>
+                Les classes immuables, <literal>mutable="false"</literal>, ne peuvent 
+                pas être modifiées ou supprimées par l'application. Cela permet 
+                à Hibernate de faire quelques optimisations mineures sur les performances.
+            </para>
+            <para>
+                L'attribut optionnnel <literal>proxy</literal> permet les intialisations 
+                différées des instances persistantes de la classe. Hibernate retournera 
+                initialement des proxies CGLIB qui implémentent l'interface nommée. 
+                Le véritable objet persistant ne sera chargé que lorsque une méthode du proxy 
+                sera appelée. Voir plus bas le paragraphe abordant les proxies et le chargement différé (lazy initialization).
+            </para>
+            <para>
+                Le polymorphisme <emphasis>implicite</emphasis> 
+                signifie que les instances de la classe seront retournées par une 
+                requête qui utilise les noms de la classe ou de chacune de ses 
+                superclasses ou encore des interfaces implémentées par cette classe 
+                ou ses superclasses. Les instances des classes filles seront retournées 
+                par une requête qui utilise le nom de la classe elle même. Le polymorphisme 
+                <emphasis>explicite</emphasis>   signifie que les instances de la classe 
+                ne seront retournées que par une requête qui utilise explicitement 
+                son nom et que seules les instances des classes filles déclarées dans les éléments 
+                <literal>&lt;subclass&gt;</literal> ou <literal>&lt;joined-subclass&gt;</literal> 
+                seront retournées. Dans la majorités des cas la valeur par défaut, 
+                <literal>polymorphism="implicit"</literal>,
+                est appropriée. Le polymorphisme explicite est utile lorsque deux 
+                classes différentes sont mappées à la même table (ceci permet d'écrire 
+                une classe "légère" qui ne contient qu'une partie des colonnes de 
+                la table - voir la partie design pattern du site communautaire). 
+            </para>
+            <para>
+                L'attribut <literal>persister</literal> vous permet de customiser 
+                la stratégie utilisée pour la classe. Vous pouvez, par exemple, spécifier 
+                votre propre sous-classe de <literal>org.hibernate.persister.EntityPersister</literal> ou 
+                vous pourriez aussi créer une nouvelle implémentation de l'interface <literal>org.hibernate.persister.ClassPersister</literal> 
+                qui proposerait une persistance via, par exemple, des appels de procédures 
+                stockées, de la sérialisation vers des fichiers plats ou un annuaire LDAP. 
+                Voir <literal>org.hibernate.test.CustomPersister</literal> pour un exemple simple (d'une "persistance" 
+                vers une <literal>Hashtable</literal>).
+            </para>
+            <para>
+                Notez que les paramètres <literal>dynamic-update</literal> et <literal>dynamic-insert</literal> 
+                ne sont pas hérités par les sous-classes et peuvent donc être spécifiés 
+                pour les éléments <literal>&lt;subclass&gt;</literal> ou <literal>&lt;joined-subclass&gt;</literal>
+                Ces paramètres peuvent améliorer les performances dans certains cas, 
+                mais peuvent aussi les amoindrir. A utiliser en connaissance de causes.
+            </para>
+            <para>
+                L'utilisation de <literal>select-before-update</literal> va généralement 
+                faire baisser les performances. Ce paramètre est pratique  
+                pour prévenir l'appel inutile d'un trigger sur modification quand on 
+                réattache un graphe d'instances à une <literal>Session</literal>.
+            </para>
+            <para>
+                Si vous utilisez le <literal>dynamic-update</literal>, les différentes 
+                stratégies de verrouillage optimiste (optimistic locking) sont les suivantes:
+            </para>
+            <itemizedlist>
+                <listitem>
+                    <para>
+                        <literal>version</literal> vérifie les colonnes version/timestamp
+                    </para>
+                </listitem>
+                <listitem>
+                    <para>
+                        <literal>all</literal> vérifie toutes les colonnes
+                    </para>
+                </listitem>
+                <listitem>
+                    <para>
+                        <literal>dirty</literal> vérifie les colonnes modifiées, permettant des updates concurrents
+                    </para>
+                </listitem>
+                <listitem>
+                    <para>
+                        <literal>none</literal> pas de verrouillage optimiste
+                    </para>
+                </listitem>
+            </itemizedlist>
+            <para>
+                Nous encourageons <emphasis>très</emphasis> fortement l'utilisation 
+                de colonnes de version/timestamp pour le verrouillage optimiste 
+                avec Hibernate. C'est la meilleure stratégie en regard des performances 
+                et la seule qui gère correctement les modifications sur les objets détachés 
+                (c'est à dire lorsqu'on utilise <literal>Session.merge()</literal>).
+            </para>
+            <para>
+                Il n'y a pas de différence entre table et vue pour le mapping Hibernate, 
+                tant que c'est transparent au niveau base de données (remarquez 
+                que certaines BDD ne supportent pas les vues correctement, notamment 
+                pour les updates). Vous rencontrerez peut-être des cas où vous 
+                souhaitez utiliser une vue mais ne pouvez pas en créer sur votre BDD 
+                (par exemple à cause de schémas anciens et figés). Dans ces cas, 
+                vous pouvez mapper une entité immuable en lecture seule sur un sous-select SQL donné:
+            </para>
+            <programlisting><![CDATA[<class name="Summary">
+    <subselect>
+        select item.name, max(bid.amount), count(*)
+        from item
+        join bid on bid.item_id = item.id
+        group by item.name
+    </subselect>
+    <synchronize table="item"/>
+    <synchronize table="bid"/>
+    <id name="name"/>
+    ...
+</class>]]></programlisting>
+            <para>
+                Déclarez les tables à synchroniser avec cette entité pour assurer 
+                que le flush automatique se produise correctement,
+                et pour que les requêtes sur l'entité dérivée ne renvoient pas des données périmées.    
+                Le litéral <literal>&lt;subselect&gt;</literal> est disponible 
+                comme attribut ou comme élément de mapping.
+            </para>
+        </sect2>
+        <sect2 id="mapping-declaration-id" revision="4">
+            <title>id</title>
+            <para>
+                Les classes mappées <emphasis>doivent</emphasis> déclarer la 
+                clef primaire de la table en base de données.
+                La plupart des classes auront aussi une propriété de type 
+                javabean présentant l'identifiant unique d'une instance.
+                L'élément <literal>&lt;id&gt;</literal> sert à définir le 
+                mapping entre cette propriété et la clef primaire en base.
+            </para>
+            <programlistingco>
+                <areaspec>
+                    <area id="id1" coords="2 65"/>
+                    <area id="id2" coords="3 65"/>
+                    <area id="id3" coords="4 65"/>
+                    <area id="id4" coords="5 65"/>
+                    <area id="id5" coords="6 65"/>
+                </areaspec>
+                <programlisting><![CDATA[<id
+        name="propertyName"
+        type="typename"
+        column="column_name"
+        unsaved-value="null|any|none|undefined|id_value"
+        access="field|property|ClassName">
+
+        <generator class="generatorClass"/>
+</id>]]></programlisting>
+                <calloutlist>
+                    <callout arearefs="id1">
+                        <para>
+                            <literal>name</literal> (optionnel) : Nom de la propriété qui sert d'identifiant.
+                        </para>
+                    </callout>
+                    <callout arearefs="id2">
+                        <para>
+                            <literal>type</literal> (optionnel) : Nom indiquant le type Hibernate.
+                        </para>
+                    </callout>
+                    <callout arearefs="id3">
+                        <para>
+                            <literal>column</literal> (optionnel - le nom de la propriété est pris par défaut) : Nom de la clef primaire.
+                        </para>
+                    </callout>
+                    <callout arearefs="id4">
+                        <para>
+                            <literal>unsaved-value</literal> (optionnel - par défaut une valeur "bien choisie") : 
+                            Une valeur de la propriété d'identifiant qui indique que l'instance est nouvellement
+                            instanciée (non sauvegardée), et qui la distingue des instances <literal>transient</literal>s qui ont
+                            été sauvegardées ou chargées dans une session précédente.
+                        </para>
+                    </callout>
+                    <callout arearefs="id5">
+                        <para>
+                            <literal>access</literal> (optionnel - par défaut <literal>property</literal>) : La stratégie que doit utiliser Hibernate 
+                            pour accéder aux valeurs des propriétés.
+                        </para>
+                    </callout>
+                </calloutlist>
+            </programlistingco>
+            <para>
+                Si l'attribut <literal>name</literal> est absent, Hibernate considère que la classe ne possède pas de propriété identifiant.
+            </para>
+            <para>
+                L'attribut <literal>unsaved-value</literal> est important ! Si 
+                l'identifiant de votre classe n'a pas une valeur par défaut compatible avec 
+                le comportement standard de Java (zéro ou null), vous devez alors préciser la valeur par défaut.
+            </para>
+            <para>
+                La déclaration alternative <literal>&lt;composite-id&gt;</literal> 
+                permet l'acccès aux données d'anciens systèmes qui utilisent des
+                clefs composées. Son utilisation est fortement déconseillée pour d'autres cas.
+            </para>
+            <sect3 id="mapping-declaration-id-generator" revision="2">
+                <title>Generator</title>
+                <para>
+                        L'élément fils <literal>&lt;generator&gt;</literal> nomme une classe Java utilisée pour générer 
+                        les identifiants uniques pour les instances des classes persistantes. Si des paramètres sont requis 
+                        pour configurer ou initialiser l'instance du générateur, ils sont passés en utilisant l'élément <literal>&lt;param&gt;</literal>.
+                </para>
+                <programlisting><![CDATA[<id name="id" type="long" column="cat_id">
+        <generator class="org.hibernate.id.TableHiLoGenerator">
+                <param name="table">uid_table</param>
+                <param name="column">next_hi_value_column</param>
+        </generator>
+</id>]]></programlisting>
+                <para>
+                        Tous les générateurs doivent implémenter l'interface <literal>org.hibernate.id.IdentifierGenerator</literal>.
+                        C'est une interface très simple ; certaines applications peuvent proposer leur propre implémentations spécialisées. 
+                        Cependant, Hibernate propose une série d'implémentations intégrées. Il existe des noms raccourcis pour les générateurs intégrés :
+                    <variablelist>
+                        <varlistentry>
+                            <term>
+                                <literal>increment</literal>
+                            </term>
+                            <listitem>
+                                <para>
+                                    Génère des identifiants de type <literal>long</literal>, <literal>short</literal> ou
+                                    <literal>int</literal> qui ne sont uniques que si aucun autre processus n'insère de données dans la même table.
+                                    <emphasis>Ne pas utiliser en environnement clusterisé.</emphasis>
+                                </para>
+                            </listitem>
+                        </varlistentry>
+                        <varlistentry>
+                            <term>
+                                <literal>identity</literal>
+                            </term>
+                            <listitem>
+                                <para>
+                                    Utilisation de la colonne identity de DB2, MySQL, MS SQL Server, Sybase et
+                                    HypersonicSQL. L'identifiant renvoyé est de type <literal>long</literal>,
+                                    <literal>short</literal> ou <literal>int</literal>.
+                            </para>
+                            </listitem>
+                        </varlistentry>
+                        <varlistentry>
+                            <term>
+                                <literal>sequence</literal>
+                            </term>
+                            <listitem>
+                                <para>
+                                    Utilisation des séquences dans  DB2, PostgreSQL, Oracle, SAP DB, McKoi ou d'un générateur dans Interbase.
+                                    L'identifiant renvoyé est de type <literal>long</literal>,
+                                    <literal>short</literal> ou <literal>int</literal>
+                                </para>
+                            </listitem>
+                        </varlistentry>
+                        <varlistentry>
+                            <term>
+                                <literal>hilo</literal>
+                            </term>
+                            <listitem>
+                                <para id="mapping-declaration-id-hilodescription" revision="1">
+                                    Utilise un algorithme hi/lo pour générer de façon efficace des identifiants de type
+                                    <literal>long</literal>, <literal>short</literal> ou <literal>int</literal>,
+                                    en prenant comme source de valeur "hi" une table et une colonne (par défaut 
+                                    <literal>hibernate_unique_key</literal> et
+                                    <literal>next_hi</literal> respectivement). L'algorithme hi/lo génère des identifiants uniques 
+                                    pour une base de données particulière seulement.
+                            </para>
+                            </listitem>
+                        </varlistentry>
+                        <varlistentry>
+                            <term>
+                                <literal>seqhilo</literal>
+                            </term>
+                            <listitem>
+                                <para>
+                                    Utilise un algorithme hi/lo pour générer efficacement des identifiants de type                                      <literal>long</literal>, <literal>short</literal> ou <literal>int</literal>,
+                                    étant donné un nom de séquence en base.
+                            </para>
+                            </listitem>
+                        </varlistentry>
+                        <varlistentry>
+                            <term>
+                                <literal>uuid</literal>
+                            </term>
+                            <listitem>
+                                <para>
+                                    Utilise un algorithme de type UUID 128 bits pour générer des identifiants de 
+                                    type string, unique au sein d'un réseau (l'adresse IP est utilisée). 
+                                    Le UUID en codé en une chaîne de nombre héxadécimaux de longueur 32.
+                            </para>
+                            </listitem>
+                        </varlistentry>
+                        <varlistentry>
+                            <term>
+                                <literal>guid</literal>
+                            </term>
+                            <listitem>
+                                <para>
+                                    Utilise une chaîne GUID générée par la base pour MS SQL Server et MySQL.
+                            </para>
+                            </listitem>
+                        </varlistentry>
+                        <varlistentry>
+                            <term>
+                                <literal>native</literal>
+                            </term>
+                            <listitem>
+                                <para>
+                                    Choisit <literal>identity</literal>, <literal>sequence</literal> ou
+                                    <literal>hilo</literal> selon les possibilités offertes par la base de données sous-jacente.
+                            </para>
+                            </listitem>
+                        </varlistentry>
+                        <varlistentry>
+                            <term>
+                                <literal>assigned</literal>
+                            </term>
+                            <listitem>
+                                <para>
+                                    Laisse l'application affecter un identifiant à l'objet avant que la métode 
+                                    <literal>save()</literal> soit appelée. Il s'agit de la stratégie par défaut 
+                                    si aucun <literal>&lt;generator&gt;</literal> n'est spécifié.
+                            </para>
+                            </listitem>
+                        </varlistentry>
+                        <varlistentry>
+                            <term>
+                                <literal>select</literal>
+                            </term>
+                            <listitem>
+                                <para>
+                                    Récupère une clef primaire assignée par un trigger en sélectionnant 
+                                    la ligne par une clef unique quelconque.
+                            </para>
+                            </listitem>
+                        </varlistentry>
+                        <varlistentry>
+                            <term>
+                                <literal>foreign</literal>
+                            </term>
+                            <listitem>
+                                <para>
+                                    Utilise l'identifiant d'un objet associé. Habituellement utilisé en conjonction
+                                    avec une association <literal>&lt;one-to-one&gt;</literal> sur la clef primaire.
+                            </para>
+                            </listitem>
+                        </varlistentry>
+                    </variablelist>
+                </para>
+            </sect3>
+            <sect3 id="mapping-declaration-id-hilo" revision="1">
+                <title>algorithme Hi/lo</title>
+                <para>
+                    Les générateurs <literal>hilo</literal> et <literal>seqhilo</literal> proposent deux implémentations
+                    alternatives de l'algorithme hi/lo, une approche largement utilisée pour générer des identifiants. La 
+                    première implémentation nécessite une table "spéciale" en base pour héberger la prochaine valeur "hi" disponible.
+                    La seconde utilise une séquence de type Oracle (quand la base sous-jacente le propose).
+                </para>
+                <programlisting><![CDATA[<id name="id" type="long" column="cat_id">
+        <generator class="hilo">
+                <param name="table">hi_value</param>
+                <param name="column">next_value</param>
+                <param name="max_lo">100</param>
+        </generator>
+</id>]]></programlisting>
+                <programlisting><![CDATA[<id name="id" type="long" column="cat_id">
+        <generator class="seqhilo">
+                <param name="sequence">hi_value</param>
+                <param name="max_lo">100</param>
+        </generator>
+</id>]]></programlisting>
+                <para>
+                    Malheureusement, vous ne pouvez pas utilisez <literal>hilo</literal> quand vous apportez 
+                    votre propre <literal>Connection</literal> à Hibernate. Quand Hibernate utilise une datasource du serveur 
+                    d'application pour obtenir des connexions inscrites avec JTA, vous devez correctement configurer 
+                    <literal>hibernate.transaction.manager_lookup_class</literal>.
+                </para>
+            </sect3>
+            <sect3 id="mapping-declaration-id-uuid">
+                <title>UUID algorithm</title>
+                <para>
+                    Le contenu du UUID est : adresse IP, date de démarrage de la JVM (précis au quart de seconde), 
+                    l'heure système et un compteur (unique au sein de la JVM). Il n'est pas possible d'obtenir l'adresse 
+                    MAC ou une adresse mémoire à partir de Java, c'est donc le mieux que l'on puisse faire sans utiliser JNI.
+                </para>
+            </sect3>
+            <sect3 id="mapping-declaration-id-sequences">
+                <title>Colonnes identifiantes et séquences</title>
+                <para>
+                    Pour les bases qui implémentent les colonnes "identité" (DB2, MySQL, Sybase, MS SQL), 
+                    vous pouvez utiliser la génération de clef par <literal>identity</literal>. 
+                    Pour les bases qui implémentent les séquences (DB2, Oracle, PostgreSQL, Interbase, McKoi, SAP DB) 
+                    vous pouvez utiliser la génération de clef par <literal>sequence</literal>. Ces deux méthodes nécessitent
+                    deux requêtes SQL pour insérer un objet.
+                </para>
+                <programlisting><![CDATA[<id name="id" type="long" column="person_id">
+        <generator class="sequence">
+                <param name="sequence">person_id_sequence</param>
+        </generator>
+</id>]]></programlisting>
+                <programlisting><![CDATA[<id name="id" type="long" column="person_id" unsaved-value="0">
+        <generator class="identity"/>
+</id>]]></programlisting>
+                   <para>Pour le développement multi-plateformes, la stratégie <literal>native</literal> choisira
+                    entre les méthodes <literal>identity</literal>, <literal>sequence</literal> et
+                    <literal>hilo</literal>, selon les possibilités offertes par la base sous-jacente.
+                </para>
+            </sect3>
+            <sect3 id="mapping-declaration-id-assigned">
+                <title>Identifiants assignés</title>
+                <para>
+                    Si vous souhaitez que l'application assigne des identifiants (par opposition 
+                    à la génération par Hibernate), vous pouvez utiliser le générateur  <literal>assigned</literal>.
+                    Ce générateur spécial utilisera une valeur d'identifiant déjà utilisé par la propriété identifiant l'objet.
+                    Ce générateur est utilisé quand la clef primaire est une clef naturelle plutôt qu'une clef secondaire.
+                    C'est le comportement par défaut si vous ne précisez pas d'élément <literal>&lt;generator&gt;</literal>.
+                </para>
+                <para>
+                    Choisir le générateur <literal>assigned</literal> fait utiliser
+                    <literal>unsaved-value="undefined"</literal> par Hibernate, le forçant à interroger
+                    la base pour déterminer si l'instance est transiente ou détachée, à moins d'utiliser 
+                    une propriété version ou timestamp, ou alors de définir 
+                    <literal>Interceptor.isUnsaved()</literal>.
+                </para>
+            </sect3>
+            <sect3 id="mapping-declaration-id-select">
+                <title>Clefs primaires assignées par trigger</title>
+                <para>
+                    Pour les schémas de base hérités d'anciens systèmes uniquement (Hibernate ne génère pas de DDL avec des triggers)  
+                </para>
+                <programlisting><![CDATA[<id name="id" type="long" column="person_id">
+        <generator class="select">
+                <param name="key">socialSecurityNumber</param>
+        </generator>
+</id>]]></programlisting>
+                <para>
+                    Dans l'exemple ci-dessus, <literal>socialSecurityNumber</literal> a une 
+                    valeur unique définie par la classe en tant que clef naturelle et <literal>person_id</literal> 
+                    est une clef secondaire dont la valeur est générée par trigger.
+                </para>
+            </sect3>
+        </sect2>
+        <sect2 id="mapping-declaration-compositeid" revision="3">
+            <title>composite-id</title>
+            <programlisting><![CDATA[<composite-id
+        name="propertyName"
+        class="ClassName"
+        mapped="true|false"
+        access="field|property|ClassName">
+        node="element-name|."
+
+        <key-property name="propertyName" type="typename" column="column_name"/>
+        <key-many-to-one name="propertyName class="ClassName" column="column_name"/>
+        ......
+</composite-id>]]></programlisting>
+            <para>
+               Pour une table avec clef composée, vous pouvez mapper plusieurs attributs de la classe 
+               comme propriétés identifiantes. L'élement <literal>&lt;composite-id&gt;</literal> accepte 
+               les mappings de propriétés <literal>&lt;key-property&gt;</literal> et les mappings 
+               <literal>&lt;key-many-to-one&gt;</literal> comme fils.
+            </para>
+            <programlisting><![CDATA[<composite-id>
+        <key-property name="medicareNumber"/>
+        <key-property name="dependent"/>
+</composite-id>]]></programlisting>
+            <para>
+                Vos classes persistantes <emphasis>doivent</emphasis> surcharger les méthodes <literal>equals()</literal> 
+                et <literal>hashCode()</literal> pour implémenter l'égalité d'identifiant composé. Elles doivent aussi 
+                implenter l'interface <literal>Serializable</literal>.
+            </para>
+            <para>
+                Malheureusement cette approche sur les identifiants composés signifie qu'un objet persistant
+                est son propre identifiant. Il n'y a pas d'autre moyen pratique de manipuler l'objet que par l'objet lui-même.
+                Vous devez instancier une instance de la classe persistante elle-même et peupler ses attributs identifiants 
+                avant de pouvoir appeler la méthode <literal>load()</literal> pour charger son état persistant associé 
+                à une clef composée. Nous appelons cette approche "identifiant composé <emphasis>embarqué</emphasis>"
+                et ne la recommandons pas pour des applications complexes.
+            </para>
+            
+            <para>
+                Une seconde approche, appelée identifiant composé <emphasis>mappé</emphasis>,
+                consiste à encapsuler les propriétés identifiantes (celles contenues dans <literal>&lt;composite-id&gt;</literal>)
+                dans une classe particulière.
+            </para>
+                
+            <programlisting><![CDATA[<composite-id class="MedicareId" mapped="true">
+        <key-property name="medicareNumber"/>
+        <key-property name="dependent"/>
+</composite-id>]]></programlisting>
+
+            <para>
+                Dans cet exemple, la classe d'identifiant composée,<literal>MedicareId</literal> et la classe mappée elle-même,
+                possèdent les propriétés <literal>medicareNumber</literal>
+                et <literal>dependent</literal>. La classe identifiante doit redéfinir
+                <literal>equals()</literal> et <literal>hashCode()</literal> et implémenter 
+                <literal>Serializable</literal>. Le désavantage de cette approche est la
+                duplication du code.
+            </para>
+            
+            <para>
+                Les attributs suivants servent à configurer un identifiant composé mappé :
+            </para>
+            <itemizedlist spacing="compact">
+                <listitem>
+                    <para>
+                        <literal>mapped</literal> (optionnel, défaut à <literal>false</literal>) :
+                        indique qu'un identifiant composé mappé est utilisé, et que les propriétés
+                        contenues font référence aux deux classes (celle mappée et la classe identifiante).
+                    </para>
+                </listitem>
+                <listitem>
+                    <para>
+                        <literal>class</literal> (optionnel, mais requis pour un identifiant composé mappé) : 
+                        La classe composant utilisée comme identifiant composé.
+                    </para>
+                </listitem>
+            </itemizedlist>
+            <para>
+                Nous décrirons une troisième approche beaucoup plus efficace ou l'identifiant composé
+                est implémenté comme une classe composant dans <xref linkend="components-compositeid"/>. 
+                Les attributs décrits ci dessous, ne s'appliquent que pour cette dernière approche :
+            </para>
+
+            <itemizedlist spacing="compact">
+                <listitem>
+                    <para>
+                        <literal>name</literal> (optionnel, requis pour cette approche) : une propriété de type
+                        composant qui contient l'identifiant composé (voir chapitre 9).
+                    </para>
+                </listitem>
+                <listitem>
+                    <para>
+                        <literal>access</literal> (optionnel - défaut à <literal>property</literal>) :
+                        La stratégie qu'Hibernate utilisera pour accéder à la valeur de la propriété.
+                    </para>
+                </listitem>
+                <listitem>
+                    <para>
+                        <literal>class</literal> (optionnel - défaut au type de la propriété déterminé par réflexion) : 
+                        La classe composant utilisée comme identifiant (voir prochaine section).
+                    </para>
+                </listitem>
+            </itemizedlist>
+            
+            <para>
+                Cette dernière approche est celle que nous recommandons pour toutes vos applications.
+            </para>
+        </sect2>
+        <sect2 id="mapping-declaration-discriminator" revision="3">
+            <title>discriminator</title>
+            <para>
+                   L'élément <literal>&lt;discriminator&gt;</literal> est nécessaire pour la persistance polymorphique 
+                   qui utilise la stratégie de mapping de table par hiérarchie de classe. La colonne discriminante contient 
+                   une valeur marqueur qui permet à la couche de persistance de savoir quelle 
+                   sous-classe instancier pour une ligne particulière de table en base. Un nombre restreint de types 
+                   peuvent être utilisés :
+                <literal>string</literal>, <literal>character</literal>, <literal>integer</literal>, 
+                <literal>byte</literal>, <literal>short</literal>, <literal>boolean</literal>, 
+                <literal>yes_no</literal>, <literal>true_false</literal>.
+            </para>
+            <programlistingco>
+                <areaspec>
+                    <area id="discriminator1" coords="2 60"/>
+                    <area id="discriminator2" coords="3 60"/>
+                    <area id="discriminator3" coords="4 60"/>
+                    <area id="discriminator4" coords="5 60"/>
+                    <area id="discriminator5" coords="6 60"/>
+                </areaspec>
+                <programlisting><![CDATA[<discriminator
+        column="discriminator_column"
+        type="discriminator_type"
+        force="true|false"
+        insert="true|false"
+        formula="arbitrary sql expression"
+/>]]></programlisting>
+                <calloutlist>
+                    <callout arearefs="discriminator1">
+                        <para>
+                            <literal>column</literal> (optionnel - par défaut à <literal>class</literal>) le 
+                            nom de la colonne discriminante.
+                        </para>
+                    </callout>
+                    <callout arearefs="discriminator2">
+                        <para>
+                            <literal>type</literal> (optionnel - par défaut à <literal>string</literal>) un nom 
+                            indiquant le type Hibernate.
+                        </para>
+                    </callout>
+                    <callout arearefs="discriminator3">
+                        <para>
+                            <literal>force</literal> (optionnel - par défaut à <literal>false</literal>) 
+                                   "oblige" Hibernate à spécifier une valeur discriminante autorisée même quand on récupère 
+                                   toutes les instances de la classe de base.
+                        </para>
+                    </callout>
+                    <callout arearefs="discriminator4">
+                        <para>
+                            <literal>insert</literal> (optionnel - par défaut à <literal>true</literal>)
+                                   à passer à  <literal>false</literal> si la colonne discriminante fait aussi partie 
+                                   d'un identifiant composé mappé (Indique à Hibernate de ne pas inclure la colonne 
+                                   dans les <literal>INSERT</literal> SQL).
+                        </para>
+                    </callout>
+                    <callout arearefs="discriminator5">
+                        <para>
+                            <literal>formula</literal> (optionnel) une expression SQL arbitraire qui est exécutée 
+                            quand un type doit être évalué. Permet la discrimination basée sur le contenu.
+                        </para>
+                    </callout>
+                </calloutlist>
+            </programlistingco>
+            <para>
+                   Les véritables valeurs de la colonne discriminante sont spécifiées par l'attribut 
+                <literal>discriminator-value</literal> des éléments <literal>&lt;class&gt;</literal> et 
+                <literal>&lt;subclass&gt;</literal>.
+            </para>
+            <para>
+                L'attribut <literal>force</literal> n'est utile que si la table contient des lignes avec des 
+                valeurs "extra" discriminantes qui ne sont pas mappées à une classe persistante. Ce ne sera généralement pas le cas.
+            </para>
+            <para>
+                En utilisant l'attribut <literal>formula</literal> vous pouvez déclarer une expression SQL arbitraire 
+                qui sera utilisée pour évaluer le type d'une ligne :
+            </para>
+            <programlisting><![CDATA[<discriminator
+    formula="case when CLASS_TYPE in ('a', 'b', 'c') then 0 else 1 end"
+    type="integer"/>]]></programlisting>
+        </sect2>
+        <sect2 id="mapping-declaration-version" revision="4">
+            <title>version (optionnel)</title>
+            <para>
+                   L'élément <literal>&lt;version&gt;</literal> est optionnel et indique que la table contient 
+                   des données versionnées. C'est particulièrement utile si vous avez l'intention d'utiliser 
+                   des <emphasis>transactions longues</emphasis> (voir plus-bas).   
+            </para>
+            <programlistingco>
+                <areaspec>
+                    <area id="version1" coords="2 60"/>
+                    <area id="version2" coords="3 60"/>
+                    <area id="version3" coords="4 60"/>
+                    <area id="version4" coords="5 60"/>
+                    <area id="version5" coords="6 60"/>
+                    <area id="version6" coords="7 70"/>
+                    <area id="version7" coords="8 70"/>
+                </areaspec>
+                <programlisting><![CDATA[<version
+        column="version_column"
+        name="propertyName"
+        type="typename"
+        access="field|property|ClassName"
+        unsaved-value="null|negative|undefined"
+        generated="never|always"
+        insert="true|false"
+        node="element-name|@attribute-name|element/@attribute|."
+/>]]></programlisting>
+                <calloutlist>
+                    <callout arearefs="version1">
+                        <para>
+                            <literal>column</literal> (optionnel - par défaut égal au nom de la propriété) : Le nom de la colonne 
+                            contenant le numéro de version.
+                        </para>
+                    </callout>
+                    <callout arearefs="version2">
+                        <para>
+                            <literal>name</literal> : Le nom d'un attribut de la classe persistante.
+                        </para>
+                    </callout>
+                    <callout arearefs="version3">
+                        <para>
+                            <literal>type</literal> (optionnel - par défaut à <literal>integer</literal>) : 
+                            Le type du numéro de version.
+                        </para>
+                    </callout>
+                    <callout arearefs="version4">
+                        <para>
+                            <literal>access</literal> (optionnel - par défaut à <literal>property</literal>) : La stratégie 
+                            à utiliser par Hibernate pour accéder à la valeur de la propriété.
+                        </para>
+                    </callout>
+                    <callout arearefs="version5">
+                        <para>
+                            <literal>unsaved-value</literal> (optionnel - par défaut à <literal>undefined</literal>) : 
+                            Une valeur de la propriété d'identifiant qui indique que l'instance est nouvellement 
+                            instanciée (non sauvegardée), et qui la distingue des instances détachées qui ont 
+                            été sauvegardées ou chargées dans une session précédente (<literal>undefined</literal> indique 
+                            que la valeur de l'atribut identifiant devrait être utilisé).
+                        </para>
+                    </callout>
+                    <callout arearefs="version6">
+                        <para>
+                            <literal>generated</literal> (optional - défaut à <literal>never</literal>) :
+                            Indique que la valeur de la propriété version est générée par la base de données
+                            cf. <xref linkend="mapping-generated">generated properties</xref>.
+                        </para>
+                    </callout>
+                    <callout arearefs="version7">
+                        <para>
+                            <literal>insert</literal> (optionnel - défaut à <literal>true</literal>) :
+                            Indique si la colonne de version doit être incluse dans les ordres insert.
+                            Peut être à <literal>false</literal> si et seulement si la colonne de la
+                            base de données est définie avec une valeur par défaut à <literal>0</literal>.
+                        </para>
+                    </callout>
+                </calloutlist>
+            </programlistingco>
+            <para>
+                Les numéros de version doivent avoir les types Hibernate <literal>long</literal>, <literal>integer</literal>,
+                <literal>short</literal>, <literal>timestamp</literal> ou <literal>calendar</literal>.
+            </para>
+            <para>
+                   Une propriété de version ou un timestamp ne doit jamais être null pour une instance 
+                   détachée, ainsi Hibernate pourra détecter toute instance ayant une version ou un timestamp null 
+                   comme transient, quelles que soient les stratégies <literal>unsaved-value</literal> spécifiées.
+                   <emphasis>Déclarer un numéro de version ou un timestamp "nullable" est un moyen pratique d'éviter 
+                   tout problème avec les réattachements transitifs dans Hibernate, particulièrement utile pour ceux qui 
+                   utilisent des identifiants assignés ou des clefs composées !</emphasis>
+            </para>
+        </sect2>
+        <sect2 id="mapping-declaration-timestamp"  revision="3" >
+            <title>timestamp (optionnel)</title>
+            <para>
+                   L'élément optionnel <literal>&lt;timestamp&gt;</literal> indique que la table contient des données 
+                   horodatées (timestamp). Cela sert d'alternative à l'utilisation de numéros de version. Les timestamps (ou horodatage) 
+                   sont par nature une implémentation moins fiable pour l'optimistic locking. Cependant, l'application 
+                   peut parfois utiliser l'horodatage à d'autres fins.
+            </para>
+            <programlistingco>
+                <areaspec>
+                    <area id="timestamp1" coords="2 45"/>
+                    <area id="timestamp2" coords="3 45"/>
+                    <area id="timestamp3" coords="4 45"/>
+                    <area id="timestamp4" coords="5 45"/>
+                    <area id="timestamp5" coords="6 70" />
+                    <area id="timestamp6" coords="7 70" />
+                </areaspec>
+                <programlisting><![CDATA[<timestamp
+        column="timestamp_column"
+        name="propertyName"
+        access="field|property|ClassName"
+        unsaved-value="null|undefined"
+        source="vm|db"
+        generated="never|always"
+        node="element-name|@attribute-name|element/@attribute|."
+/>]]></programlisting>
+                <calloutlist>
+                    <callout arearefs="timestamp1">
+                        <para>
+                            <literal>column</literal> (optionnel - par défaut à le nom de la propriété) : Le nom d'une colonne 
+                            contenant le timestamp.
+                        </para>
+                    </callout>
+                    <callout arearefs="timestamp2">
+                        <para>
+                            <literal>name</literal> : Le nom d'une propriété au sens JavaBean de type 
+                            <literal>Date</literal> ou <literal>Timestamp</literal> de la classe persistante.
+                        </para>
+                    </callout>
+                    <callout arearefs="timestamp3">
+                        <para>
+                            <literal>access</literal> (optionnel - par défaut à <literal>property</literal>) : La stratégie 
+                            à utiliser par Hibernate pour accéder à la valeur de la propriété.
+                        </para>
+                    </callout>
+                    <callout arearefs="timestamp4">
+                        <para>
+                            <literal>unsaved-value</literal> (optionnel - par défaut à <literal>null</literal>) : 
+                              Propriété dont la valeur est un numéro de version qui indique que l'instance est nouvellement 
+                              instanciée (non sauvegardée), et qui la distingue des instances détachées qui ont 
+                              été sauvegardées ou chargées dans une session précédente (<literal>undefined</literal> indique 
+                              que la valeur de l'attribut identifiant devrait être utilisée).
+                        </para>
+                    </callout>
+                    <callout arearefs="timestamp5">
+                        <para>
+                            <literal>source</literal> (optionnel - par défaut à <literal>vm</literal>) :
+                            D'où Hibernate doit-il récupérer la valeur du timestamp? Depuis la base de données
+                            ou depuis la JVM d'exécution? Les valeurs de timestamp de la base de données provoquent
+                            une surcharge puisque Hibernate doit interroger la base pour déterminer la prochaine valeur
+                            mais cela est plus sûr lorsque vous fonctionnez dans un cluster. Remarquez aussi que
+                            certains des dialectes ne supportent pas cette fonction, et que d'autres l'implémentent
+                            mal, provoquant des erreurs de précision (Oracle 8 par exemple).
+                        </para>
+                    </callout>
+                    <callout arearefs="timestamp6">
+                        <para>
+                            <literal>generated</literal> (optional - défaut à <literal>never</literal>) :
+                            Indique que la valeur de ce timestamp est générée par la base de données
+                            cf. <xref linkend="mapping-generated">generated properties</xref>.
+                        </para>
+                    </callout>
+                </calloutlist>
+            </programlistingco>
+            <para>
+                Notez que <literal>&lt;timestamp&gt;</literal> est équivalent à 
+                <literal>&lt;version type="timestamp"&gt;</literal>.
+            </para>
+        </sect2>
+        <sect2 id="mapping-declaration-property" revision="4">
+            <title>property</title>
+            <para>
+                L'élément <literal>&lt;property&gt;</literal> déclare une propriété de la classe au sens JavaBean.
+            </para>
+            <programlistingco>
+                <areaspec>
+                    <area id="property1" coords="2 45"/>
+                    <area id="property2" coords="3 45"/>
+                    <area id="property3" coords="4 45"/>
+                    <areaset id="property4-5" coords="">
+                        <area id="property4" coords="5 45"/>
+                        <area id="property5" coords="6 45"/>
+                    </areaset>
+                    <area id="property6" coords="7 45"/>
+                    <area id="property7" coords="8 45"/>
+                    <area id="property8" coords="9 45"/>
+                    <area id="property9" coords="10 45"/>
+                    <area id="property10" coords="11 45"/>
+                    <area id="property11" coords="12 45"/>
+                    <area id="property12" coords="13 70"/>
+                </areaspec>
+                <programlisting><![CDATA[<property
+        name="propertyName"
+        column="column_name"
+        type="typename"
+        update="true|false"
+        insert="true|false"
+        formula="arbitrary SQL expression"
+        access="field|property|ClassName"
+        lazy="true|false"
+        unique="true|false"
+        not-null="true|false"
+        optimistic-lock="true|false"
+        generated="never|insert|always"
+        node="element-name|@attribute-name|element/@attribute|."
+        index="index_name"
+        unique_key="unique_key_id"
+        length="L"
+        precision="P"
+        scale="S"
+/>]]></programlisting>
+                <calloutlist>
+                    <callout arearefs="property1">
+                        <para>
+                            <literal>name</literal> : nom de la propriété, avec une lettre initiale en minuscule.
+                        </para>
+                    </callout>
+                    <callout arearefs="property2">
+                        <para>
+                            <literal>column</literal> (optionnel - par défaut au nom de la propriété) : le nom 
+                                   de la colonne mappée. Cela peut aussi être indiqué dans le(s) sous-élément(s) 
+                            <literal>&lt;column&gt;</literal>.
+                        </para>
+                    </callout>
+                    <callout arearefs="property3">
+                        <para>
+                            <literal>type</literal> (optionnel) : nom indiquant le type Hibernate.
+                        </para>
+                    </callout>
+                    <callout arearefs="property4-5">
+                        <para>
+                            <literal>update, insert</literal> (optionnel - par défaut à <literal>true</literal>) :
+                           indique que les colonnes mappées devraient être incluses dans des <literal>UPDATE</literal> SQL 
+                           et/ou des <literal>INSERT</literal>. Mettre les deux à <literal>false</literal> 
+                           empêche la propagation en base de données (utile si vous savez qu'un trigger affectera la valeur à la  colonne). 
+                        </para>
+                    </callout>
+                    <callout arearefs="property6">
+                        <para>
+                            <literal>formula</literal> (optionnel) : une expression SQL qui définit la valeur pour une propriété 
+                            <emphasis>calculée</emphasis>. Les propriétés calculées ne possède pas leur propre mapping.
+                        </para>
+                    </callout>
+                    <callout arearefs="property7">
+                        <para>
+                            <literal>access</literal> (optionnel - par défaut à <literal>property</literal>): Stratégie que Hibernate
+                             doit utiliser pour accéder à cette valeur.
+                        </para>
+                    </callout>
+                    <callout arearefs="property8">
+                        <para>
+                            <literal>lazy</literal> (optionnel - par défaut à <literal>false</literal>): Indique 
+                            que cette propriété devrait être chargée en différé (lazy loading) quand on accède à la variable 
+                            d'instance pour la première fois.
+                        </para>
+                    </callout>
+                    <callout arearefs="property9">
+                        <para>
+                            <literal>unique</literal> (optionnel): Génère le DDL d'une contrainte d'unicité pour les colonnes. 
+                            Permet aussi d'en faire la cible d'un <literal>property-ref</literal>.
+                        </para>
+                    </callout>
+                    <callout arearefs="property10">
+                        <para>
+                            <literal>not-null</literal> (optionnel): Génère le DDL d'une contrainte de non nullité pour les colonnes.
+                        </para>
+                    </callout>
+                    <callout arearefs="property11">
+                        <para>
+                            <literal>optimistic-lock</literal> (optionnel - par défaut à <literal>true</literal>): 
+                            Indique que les mises à jour de cette propriété peuvent ou non nécessiter l'acquisition 
+                            d'un verrou optimiste. En d'autres termes, cela détermine s'il est nécessaire d'incrémenter 
+                            un numéro de version quand cette propriété est marquée obsolète (dirty).
+                        </para>                 
+                    </callout>
+                    <callout arearefs="property12">
+                        <para>
+                            <literal>generated</literal> (optional - défaut à<literal>never</literal>):
+                            Indique que la valeur de ce timestamp est générée par la base de données
+                            cf. <xref linkend="mapping-generated">generated properties</xref>.
+                        </para>
+                    </callout>
+                </calloutlist>
+            </programlistingco>
+            <para>
+                <emphasis>typename</emphasis> peut être:
+            </para>
+            <orderedlist spacing="compact">
+                <listitem>
+                    <para>
+                        Nom d'un type basique Hibernate (ex: <literal>integer, string, character,
+                        date, timestamp, float, binary, serializable, object, blob</literal>).
+                    </para>
+                </listitem>
+                <listitem>
+                    <para>
+                        Nom d'une classe Java avec un type basique par défaut (ex: <literal>int, float,
+                        char, java.lang.String, java.util.Date, java.lang.Integer, java.sql.Clob</literal>).
+                    </para>
+                </listitem>
+                <listitem>
+                    <para>
+                        Nom d'une classe Java sérialisable.
+                    </para>
+                </listitem>
+                <listitem>
+                    <para>
+                       Nom d'une classe ayant un type spécifique (ex: <literal>com.illflow.type.MyCustomType</literal>).
+                    </para>
+                </listitem>
+            </orderedlist>
+            <para>
+                   Si vous n'indiquez pas un type, Hibernate utlisera la réflexion sur le nom de la propriété 
+                   pour tenter de trouver le type Hibernate correct. Hibernate essayera d'interprêter 
+                   le nom de la classe retournée par le getter de la propriété en utilisant les régles 2, 3, 
+                   4 dans cet ordre. Cependant, ce n'est pas toujours suffisant. Dans certains cas vous aurez 
+                   encore besoin de l'attribut <literal>type</literal> (Par exemple, pour distinguer 
+                   <literal>Hibernate.DATE</literal> et <literal>Hibernate.TIMESTAMP</literal>, ou pour préciser 
+                   un type spécifique).
+            </para>
+            <para>
+                   L'attribut <literal>access</literal> permet de contrôler comment Hibernate accèdera 
+                   à la propriété à l'exécution. Par défaut, Hibernate utilisera les méthodes set/get. 
+                   Si vous indiquez <literal>access="field"</literal>, Hibernate ignorera les getter/setter 
+                   et accèdera à la propriété directement en utilisant la réflexion. Vous pouvez spécifier 
+                   votre propre stratégie d'accès aux propriété en donnant une classe qui implémente l'interface 
+                <literal>org.hibernate.property.PropertyAccessor</literal>.
+            </para>
+            <para>
+                   Une fonctionnalité particulièrement intéressante est les propriétés dérivées.
+                   Ces propriétés sont par définition en lecture seule, la valeur de la propriété est calculée au chargement. 
+                   Le calcul est déclaré comme une expression SQL, qui se traduit par une sous-requête <literal>SELECT</literal> 
+                   dans la requête SQL qui charge une instance :
+            </para>
+            <programlisting><![CDATA[
+<property name="totalPrice"
+    formula="( SELECT SUM (li.quantity*p.price) FROM LineItem li, Product p
+                WHERE li.productId = p.productId
+                AND li.customerId = customerId
+                AND li.orderNumber = orderNumber )"/>]]></programlisting>
+            <para>
+                   Remarquez que vous pouvez référencer la propre table des entités en ne déclarant pas un 
+                   alias sur une colonne particulière (<literal>customerId</literal> dans l'exemple donné). 
+                   Notez aussi que vous pouvez utiliser le sous-élément de mapping <literal>&lt;formula&gt;</literal> 
+                   plutôt que d'utiliser l'attribut si vous le souhaitez.
+            </para>
+        </sect2>
+        <sect2 id="mapping-declaration-manytoone" revision="5">
+            <title>many-to-one</title>
+            <para> Une association ordinaire vers une autre classe persistante est déclarée en utilisant 
+                   un élément <literal>many-to-one</literal>. Le modèle relationnel est une association 
+                   de type many-to-one : une clef étrangère dans une table référence la ou les clef(s) primaire(s) dans la table cible.
+            </para>
+            <programlistingco>
+                <areaspec>
+                    <area id="manytoone1" coords="2 60"/>
+                    <area id="manytoone2" coords="3 60"/>
+                    <area id="manytoone3" coords="4 60"/>
+                    <area id="manytoone4" coords="5 60"/>
+                    <area id="manytoone5" coords="6 60"/>
+                    <areaset id="manytoone6-7" coords="">
+                        <area id="manytoone6" coords="7 60"/>
+                        <area id="manytoone7" coords="8 60"/>
+                    </areaset>
+                    <area id="manytoone8" coords="9 60"/>
+                    <area id="manytoone9" coords="10 60"/>
+                    <area id="manytoone10" coords="11 60"/>
+                    <area id="manytoone11" coords="12 60"/>
+                    <area id="manytoone12" coords="13 60"/>
+                    <area id="manytoone13" coords="14 60"/>
+                    <area id="manytoone14" coords="15 60"/>
+                    <area id="manytoone14" coords="15 70"/>
+                    <area id="manytoone15" coords="16 70"/>
+                    <area id="manytoone16" coords="17 70"/>
+                </areaspec>
+                <programlisting><![CDATA[<many-to-one
+        name="propertyName"
+        column="column_name"
+        class="ClassName"
+        cascade="cascade_style"
+        fetch="join|select"
+        update="true|false"
+        insert="true|false"
+        property-ref="propertyNameFromAssociatedClass"
+        access="field|property|ClassName"
+        unique="true|false"
+        not-null="true|false"
+        optimistic-lock="true|false"
+        lazy="proxy|no-proxy|false"
+        not-found="ignore|exception"
+        entity-name="EntityName"
+        formula="arbitrary SQL expression"
+        node="element-name|@attribute-name|element/@attribute|."
+        embed-xml="true|false"
+        index="index_name"
+        unique_key="unique_key_id"
+        foreign-key="foreign_key_name"
+/>]]></programlisting>
+                <calloutlist>
+                    <callout arearefs="manytoone1">
+                        <para>
+                            <literal>name</literal> : Nom de la propriété.
+                        </para>
+                    </callout>
+                    <callout arearefs="manytoone2">
+                        <para>
+                            <literal>column</literal> (optionnel) : Le nom de la clef étrangère. Cela peut être 
+                            aussi indiqué avec le sous-élément <literal>&lt;column&gt;</literal>.
+                        </para>
+                    </callout>
+                    <callout arearefs="manytoone3">
+                        <para>
+                            <literal>class</literal> (optionnel - par défaut le type de la propriété déterminé 
+                            par réflexion) : Le nom de la classe associée.
+                        </para>
+                    </callout>
+                    <callout arearefs="manytoone4">
+                        <para>
+                            <literal>cascade</literal> (optionnel) : Indique quelles opérations doivent 
+                            être propagées de l'objet père vers les objets associés.
+                        </para>
+                    </callout>
+                    <callout arearefs="manytoone5">
+                        <para>
+                            <literal>fetch</literal> (optionnel - par défaut à <literal>select</literal>) : 
+                            Choisit entre le chargement de type outer-join ou le chargement par select successifs.
+                        </para>
+                    </callout>
+                    <callout arearefs="manytoone6-7">
+                        <para>
+                            <literal>update, insert</literal> (optionnel - par défaut à <literal>true</literal>) :
+                           indique que les colonnes mappées devraient être incluses dans des <literal>UPDATE</literal> SQL 
+                           et/ou des <literal>INSERT</literal>. Mettre les deux à <literal>false</literal> 
+                           empêche la propagation en base de données (utile si vous savez qu'un trigger affectera la valeur à la  colonne).                         
+                         </para>
+                    </callout>
+                    <callout arearefs="manytoone8">
+                        <para>
+                            <literal>property-ref</literal> : (optionnel) Le nom d'une propriété de la classe 
+                            associée qui est liée à cette clef étrangère. Si ce n'est pas spécifié, la clef primaire de la 
+                            classe associée est utilisée.
+                        </para>
+                    </callout>
+                    <callout arearefs="manytoone9">
+                        <para>
+                            <literal>access</literal> (optionnel - par défaut à <literal>property</literal>) : La 
+                            stratégie à utiliser par Hibernate pour accéder à la valeur de cette propriété.
+                        </para>
+                    </callout>
+                    <callout arearefs="manytoone10">
+                        <para>
+                            <literal>unique</literal> (optionnel) : Génère le DDL d'une contrainte d'unicité pour la clef étrangère. 
+                            Permet aussi d'en faire la cible d'un <literal>property-ref</literal>. Cela permet de créer une véritable 
+                            association one-to-one.
+                        </para>
+                    </callout>
+                    <callout arearefs="manytoone11">
+                        <para>
+                            <literal>not-null</literal> (optionnel) : Génère le DDL pour une contrainte de non nullité pour la clef étrangère.
+                       </para>
+                    </callout>
+                    <callout arearefs="manytoone12">
+                        <para>
+                            <literal>optimistic-lock</literal> (optionnel - par défaut à <literal>true</literal>) : 
+                            Indique que les mises à jour de cette propriété requièrent ou non l'acquisition 
+                            d'un verrou optimiste. En d'autres termes, détermine si un incrément de version doit 
+                            avoir lieu quand la propriété est marquée obsolète (dirty).
+                        </para>
+                    </callout>
+                    <callout arearefs="manytoone13">
+                        <para>
+                            <literal>lazy</literal> (optionnel - par défaut à <literal>false</literal>) : Indique 
+                            que cette propriété doit être chargée en différé (lazy loading) au premier accès 
+                            à la variable d'instance (nécessite une instrumentation du bytecode lors de la phase 
+                            de construction). Remarquez que cela n'influence pas le comportement du proxy 
+                            Hibernate - comme l'attribut <literal>lazy</literal> sur des classes ou des mappings 
+                            de collections, mais utilise l'interception pour le chargement différé.
+                            <literal>lazy="false"</literal> indique que l'association sera toujours chargée.
+                        </para>
+                    </callout>
+                    <callout arearefs="manytoone14">
+                        <para>
+                            <literal>not-found</literal> (optionnel - par défaut à <literal>exception</literal>) : 
+                            Indique comment les clefs étrangères qui référencent des lignes manquantes doivent être manipulées :
+                            <literal>ignore</literal> traitera une ligne manquante comme une association nulle.
+                        </para>
+                    </callout>
+                    <callout arearefs="manytoone15">
+                        <para>
+                            <literal>entity-name</literal> (optionnel) : Le nom de l'entité de la classe associée.
+                        </para>                   
+                    </callout>
+                    <callout arearefs="manytoone16">
+                        <para>
+                            <literal>formula</literal> (optionnel) : une expression SQL qui définit la valeur
+                            pour une clé étrangère calculée.
+                        </para>
+                    </callout>
+                </calloutlist>
+            </programlistingco>
+            <para>
+                Donner une valeur significative à l'attribut <literal>cascade</literal> autre que 
+                <literal>none</literal>  propagera certaines opérations à l'objet associé. Les valeurs 
+                significatives sont les noms des opérations Hibernate basiques,     
+                <literal>persist, merge, delete, save-update, evict, replicate, lock,
+                refresh</literal>, ainsi que les valeurs spéciales <literal>delete-orphan</literal> 
+                et <literal>all</literal> et des combinaisons de noms d'opérations séparées par des virgules,
+                comme par exemple <literal>cascade="persist,merge,evict"</literal> ou
+                <literal>cascade="all,delete-orphan"</literal>. Voir <xref linkend="objectstate-transitive"/>
+                pour une explication complète.
+                Notez que les assocations many-to-one et one-to-one ne supportent pas orphan delete.
+            </para>
+
+            <para>
+                Une déclaration <literal>many-to-one</literal> typique est aussi simple que :
+            </para>
+            <programlisting><![CDATA[<many-to-one name="product" class="Product" column="PRODUCT_ID"/>]]></programlisting>
+            <para>
+                L'attribut <literal>property-ref</literal> devrait être utilisé pour mapper seulement des données 
+                provenant d'un ancien système où les clefs étrangères font référence à une clef unique de la table associée 
+                et qui n'est pas la clef primaire. C'est un cas de mauvaise conception relationnelle.
+                Par exemple, supposez que la classe <literal>Product</literal> a un numéro de série unique qui n'est pas
+                la clef primaire. (L'attribut <literal>unique</literal> contrôle la génération DDL par Hibernate avec 
+                l'outil SchemaExport.)
+            </para>
+            <programlisting><![CDATA[<property name="serialNumber" unique="true" type="string" column="SERIAL_NUMBER"/>]]></programlisting>
+            <para>
+                Ainsi le mapping pour <literal>OrderItem</literal> peut utiliser :
+            </para>
+            <programlisting><![CDATA[<many-to-one name="product" property-ref="serialNumber" column="PRODUCT_SERIAL_NUMBER"/>]]></programlisting>
+            <para>
+                bien que ce ne soit certainement pas encouragé.
+            </para>
+            <para>
+                Si la clef unique référencée comprend des propriétés multiples de l'entité associée, vous devez mapper
+                ces propriétés à l'intérieur d'un élément <literal>&lt;properties&gt;</literal>.
+            </para>
+        </sect2>
+        <sect2 id="mapping-declaration-onetoone" revision="3">
+            <title>one-to-one</title>
+            <para>
+                Une association one-to-one vers une autre classe persistante est déclarée avec l'élément
+                <literal>one-to-one</literal>.
+            </para>
+            <programlistingco>
+                <areaspec>
+                    <area id="onetoone1" coords="2 60"/>
+                    <area id="onetoone2" coords="3 60"/>
+                    <area id="onetoone3" coords="4 60"/>
+                    <area id="onetoone4" coords="5 60"/>
+                    <area id="onetoone5" coords="6 60"/>
+                    <area id="onetoone6" coords="7 60"/>
+                    <area id="onetoone7" coords="8 60"/>
+                    <area id="onetoone8" coords="9 60"/>
+                    <area id="onetoone9" coords="10 70"/>
+                    <area id="onetoone10" coords="11 70"/>
+                </areaspec>
+                <programlisting><![CDATA[<one-to-one
+        name="propertyName"
+        class="ClassName"
+        cascade="cascade_style"
+        constrained="true|false"
+        fetch="join|select"
+        property-ref="propertyNameFromAssociatedClass"
+        access="field|property|ClassName"
+        formula="any SQL expression"
+        entity-name="EntityName"
+/>]]></programlisting>
+                <calloutlist>
+                    <callout arearefs="onetoone1">
+                        <para>
+                            <literal>name</literal> : Le nom de la propriété.
+                        </para>
+                    </callout>
+                    <callout arearefs="onetoone2">
+                        <para>
+                            <literal>class</literal> (optionnel - par défaut du type de la propriété 
+                            déterminé par réflexion) : Le nom de la classe associée.
+                        </para>
+                    </callout>
+                    <callout arearefs="onetoone3">
+                        <para>
+                            <literal>cascade</literal> (optionnel) :  Indique quelles opérations doivent 
+                            être cascadées de l'objet père vers l'objet associé.
+                        </para>
+                    </callout>
+                    <callout arearefs="onetoone4">
+                        <para>
+                            <literal>constrained</literal> (optionnel) : Indique qu'une contrainte de clef étrangère 
+                            sur la clef primaire de la table mappée référence la table de la classe associée.
+                            Cette option affecte l'ordre dans lequel chaque <literal>save()</literal> et chaque
+                            <literal>delete()</literal> sont cascadés et détermine si l'association peut utiliser un proxy 
+                            (aussi utilisé par l'outil d'export de schéma).
+                        </para>
+                    </callout>
+                    <callout arearefs="onetoone5">
+                        <para>
+                            <literal>fetch</literal> (optionnel - par défaut à <literal>select</literal>) : 
+                            Choisit entre récupération par jointure externe ou select séquentiel.
+                        </para>
+                    </callout>
+                    <callout arearefs="onetoone6">
+                        <para>
+                            <literal>property-ref</literal> (optionnel) : Le nom de la propriété de la classe associée qui est jointe à la clef
+                            primaire de cette classe. Si ce n'est pas spécifié, la clef primaire de la classe associée est utilisée.
+                        </para>
+                    </callout>
+                    <callout arearefs="onetoone7">
+                        <para>
+                            <literal>access</literal> (optionnel - par défaut à <literal>property</literal>) : 
+                            La stratégie à utiliser par Hibernate pour accéder à la valeur de la propriété.
+                        </para>
+                    </callout>
+                    <callout arearefs="onetoone8">
+                        <para>
+                            <literal>formula</literal> (optionnel) : Presque toutes les associations one-to-one pointent sur la clef primaire 
+                            de l'entité propriétaire. Dans les rares cas différents, vous devez donner une ou plusieurs 
+                            autres colonnes ou expression à joindre par une formule SQL (voir <literal>org.hibernate.test.onetooneformula</literal> pour un exemple).
+                        </para>                 
+                    </callout>
+                    <callout arearefs="onetoone9">
+                        <para>
+                            <literal>lazy</literal> (optionnel - par défaut <literal>proxy</literal>) : 
+                            Par défaut, les associations simples sont soumise à proxy. <literal>lazy="no-proxy"</literal>
+                            spécifie que la propriété doit être chargée à la demande au premier accès à l'instance.
+                            (nécessite l'intrumentation du bytecode à la construction). 
+                            <literal>lazy="false"</literal> indique que l'association sera toujours chargée
+                            agressivement. <emphasis>Notez que si <literal>constrained="false"</literal>,
+                            l'utilisation de proxy est impossible et Hibernate chargera automatiquement l'association !</emphasis>
+                        </para>
+                    </callout>
+                    <callout arearefs="onetoone10">
+                        <para>
+                            <literal>entity-name</literal> (optional) : The entity name of the associated class.
+                        </para>                   
+                    </callout>
+                </calloutlist>
+            </programlistingco>
+            <para>
+                Il existe deux types d'associations one-to-one :
+            </para>
+            <itemizedlist>
+                <listitem>
+                    <para>
+                associations par clef primaire
+            </para>
+                </listitem>
+                <listitem>
+                    <para>
+                association par clef étrangère unique
+            </para>
+                </listitem>
+            </itemizedlist>
+            <para>
+                Les associations par clef primaire ne nécessitent pas une colonne supplémentaire en table ; si deux lignes sont 
+                liés par l'association alors les deux lignes de la table partagent la même valeur de clef primaire. Donc si vous 
+                voulez que deux objets soient liés par une association par clef primaire, vous devez faire en sorte qu'on leur 
+                assigne la même valeur d'identifiant !
+            </para>
+            <para>
+                Pour une association par clef primaire, ajoutez les mappings suivants à <literal>Employee</literal> et 
+                <literal>Person</literal>, respectivement.
+            </para>
+            <programlisting><![CDATA[<one-to-one name="person" class="Person"/>]]></programlisting>
+            <programlisting><![CDATA[<one-to-one name="employee" class="Employee" constrained="true"/>]]></programlisting>
+            <para>
+                Maintenant, vous devez faire en sorte que les clefs primaires des lignes liées dans les tables PERSON et EMPLOYEE 
+                sont égales. On utilise une stratégie Hibernate spéciale de génération d'identifiants appelée 
+                <literal>foreign</literal> :
+            </para>
+            <programlisting><![CDATA[<class name="person" table="PERSON">
+    <id name="id" column="PERSON_ID">
+        <generator class="foreign">
+            <param name="property">employee</param>
+        </generator>
+    </id>
+    ...
+    <one-to-one name="employee"
+        class="Employee"
+        constrained="true"/>
+</class>]]></programlisting>
+            <para>
+                Une instance fraîchement enregistrée de <literal>Person</literal> se voit alors assignée la même valeur 
+                de clef primaire que l'instance de <literal>Employee</literal> référencée par la propriété <literal>employee</literal> 
+                de cette <literal>Person</literal>.
+            </para>
+            <para>
+                Alternativement, une clef étrangère avec contrainte d'unicité de <literal>Employee</literal> vers 
+                <literal>Person</literal> peut être indiquée ainsi :
+            </para>
+            <programlisting><![CDATA[<many-to-one name="person" class="Person" column="PERSON_ID" unique="true"/>]]></programlisting>
+            <para>
+                Et cette association peut être rendue bidirectionnelle en ajoutant ceci au mapping de <literal>Person</literal> :
+            </para>
+            <programlisting><![CDATA[<one-to-one name="employee" class="Employee" property-ref="person"/>]]></programlisting>
+        </sect2>
+        
+        <sect2 id="mapping-declaration-naturalid">
+            <title>natural-id</title>
+
+            <programlisting><![CDATA[<natural-id mutable="true|false"/>
+        <property ... />
+        <many-to-one ... />
+        ......
+</natural-id>]]></programlisting>
+
+            <para>
+                Bien que nous recommandions l'utilisation de clé primaire générée, vous devriez toujours
+                essayer d'identifier des clé métier (naturelles) pour toutes vos entités. Une clé naturelle
+                est une propriété ou une combinaison de propriétés uniques et non nulles. Si elle est aussi
+                immuable, c'est encore mieux. Mappez les propriétés de la clé naturelle dans l'élément
+                <literal>&lt;natural-id&gt;</literal>. Hibernate générera la clé unique nécessaire et les contraintes
+                de non-nullité, et votre mapping s'auto-documentera.
+            </para>
+            
+            <para>
+                Nous vous recommandons fortement d'implémenter <literal>equals()</literal> et 
+                <literal>hashCode()</literal> pour comparer les clés naturelles de l'entité.
+            </para>
+
+            <para>
+                Ce mapping n'est pas destiné à être utilisé avec des entités qui ont des clés naturelles.
+            </para>
+
+            <itemizedlist spacing="compact">
+                <listitem>
+                    <para>
+                        <literal>mutable</literal> (optionel, par défaut à <literal>false</literal>) : 
+                        Par défaut, les identifiants naturels sont supposés être immuable (constants).
+                    </para>
+                </listitem>
+            </itemizedlist>
+            
+        </sect2>
+        <sect2 id="mapping-declaration-component" revision="2">
+            <title>component, dynamic-component</title>
+            <para>
+                L'élément <literal>&lt;component&gt;</literal> mappe les propriétés d'un objet fils 
+                aux colonnes d'une classe parente. Les composants peuvent en retour déclarer leurs propres 
+                propriétés, composants ou collections. Voir "Components" plus bas.
+            </para>
+            <programlistingco>
+                <areaspec>
+                    <area id="component1" coords="2 45"/>
+                    <area id="component2" coords="3 45"/>
+                    <area id="component3" coords="4 45"/>
+                    <area id="component4" coords="5 45"/>
+                    <area id="component5" coords="6 45"/>
+                    <area id="component6" coords="7 45"/>
+                    <area id="component7" coords="8 45"/>
+                    <area id="component8" coords="9 45"/>
+                </areaspec>
+                <programlisting><![CDATA[<component 
+        name="propertyName" 
+        class="className"
+        insert="true|false"
+        update="true|false"
+        access="field|property|ClassName"
+        lazy="true|false"
+        optimistic-lock="true|false"
+        unique="true|false"
+>
+        
+        <property ...../>
+        <many-to-one .... />
+        ........
+</component>]]></programlisting>
+                <calloutlist>
+                    <callout arearefs="component1">
+                        <para>
+                            <literal>name</literal> : Nom de la propriété
+                        </para>
+                    </callout>
+                    <callout arearefs="component2">
+                        <para>
+                            <literal>class</literal> (optionnel - par défaut au type de la propriété déterminé par réflexion) : 
+                            le nom de la classe (fille) du composant.
+                        </para>
+                    </callout>
+                    <callout arearefs="component3">
+                        <para>
+                            <literal>insert</literal> : Est ce que les colonnes mappées apparaissent dans les 
+                            <literal>INSERT</literal>s ?
+                        </para>
+                    </callout>
+                    <callout arearefs="component4">
+                        <para>
+                            <literal>update</literal>: Est ce que les colonnes mappées apparaissent dans les 
+                            <literal>UPDATE</literal>s ?
+                        </para>
+                    </callout>
+                    <callout arearefs="component5">
+                        <para>
+                            <literal>access</literal> (optionnel - par défaut à <literal>property</literal>) : 
+                            La stratégie que Hibernate doit utiliser pour accéder à la valeur de cette propriété.
+                        </para>
+                    </callout>
+                    <callout arearefs="component6">
+                        <para>
+                            <literal>lazy</literal> (optionnel - par défaut à <literal>false</literal>) : 
+                            Indique que ce composant doit être chargé au premier accès 
+                            à la variable d'instance (nécessite une instrumentation du bytecode au moment du build).
+                        </para>
+                    </callout>
+                    <callout arearefs="component7">
+                        <para>
+                            <literal>optimistic-lock</literal> (optionnel - par défaut à <literal>true</literal>) :
+                                Indique que les mises à jour sur ce composant nécessitent ou non l'acquisition d'un 
+                                verrou optimiste. En d'autres termes, cela détermine si une incrémentation de version 
+                                doit avoir lieu quand la propriété est marquée obsolète (dirty).
+                            </para>
+                    </callout>
+                    <callout arearefs="component8">
+                        <para>
+                            <literal>unique</literal> (optionnel - par défaut à <literal>false</literal>) :
+                                Indique qu'une contrainte d'unicité existe sur toutes les colonnes mappées de ce composant.
+                            </para>
+                    </callout>
+                </calloutlist>
+            </programlistingco>
+            <para>
+                Les tags fils <literal>&lt;property&gt;</literal> mappent les propriétés 
+                de la classe fille sur les colonnes de la table.
+            </para>
+            <para>
+                L'élément <literal>&lt;component&gt;</literal> permet de déclarer sous-élément <literal>&lt;parent&gt;</literal> qui associe une propriété
+                de la classe composant comme une référence arrière vers l'entité contenante.
+            </para>
+            <para>
+                L'élément <literal>&lt;dynamic-component&gt;</literal> permet à une <literal>Map</literal> d'être mappée 
+                comme un composant, quand les noms de la propriété font référence aux clefs de cette Map, voir 
+                <xref linkend="components-dynamic"/>.
+            </para>
+        </sect2>
+        <sect2 id="mapping-declaration-properties" revision="2">
+            <title>properties</title>
+            <para>
+                L'élément <literal>&lt;properties&gt;</literal> permet la définition d'un groupement logique nommé 
+                des propriétés d'une classe. L'utilisation la plus importante de cette construction est la possibilité 
+                pour une combinaison de propriétés d'être la cible d'un <literal>property-ref</literal>. C'est aussi 
+                un moyen pratique de définir une contrainte d'unicité multi-colonnes.
+            </para>
+            <programlistingco>
+                <areaspec>
+                    <area id="properties1" coords="2 45"/>
+                    <area id="properties2" coords="3 45"/>
+                    <area id="properties3" coords="4 45"/>
+                    <area id="properties4" coords="5 45"/>
+                    <area id="properties5" coords="6 45"/>
+                </areaspec>
+                <programlisting><![CDATA[<properties 
+        name="logicalName" 
+        insert="true|false"
+        update="true|false"
+        optimistic-lock="true|false"
+        unique="true|false"
+>
+        
+        <property ...../>
+        <many-to-one .... />
+        ........
+</properties>]]></programlisting>
+                <calloutlist>
+                    <callout arearefs="properties1">
+                        <para>
+                            <literal>name</literal> : Le nom logique d'un regroupement et 
+                            <emphasis>non</emphasis> le véritable nom d'une propriété.
+                        </para>
+                    </callout>
+                    <callout arearefs="properties2">
+                        <para>
+                            <literal>insert</literal> : Est-ce que les colonnes mappées apparaissent dans les 
+                            <literal>INSERT</literal>s ?
+                        </para>
+                    </callout>
+                    <callout arearefs="properties3">
+                        <para>
+                            <literal>update</literal> : Est-ce que les colonnes mappées apparaissent dans les 
+                            <literal>UPDATE</literal>s ?
+                        </para>
+                    </callout>
+                    <callout arearefs="properties4">
+                        <para>
+                            <literal>optimistic-lock</literal> (optionnel - par défaut à <literal>true</literal>) :
+                                Indique que les mises à jour sur ce composant nécessitent ou non l'acquisition d'un 
+                                verrou optimiste. En d'autres termes, cela détermine si une incrémentation 
+                                de version doit avoir lieu quand la propriété est marquée obsolète (dirty).
+                            </para>
+                    </callout>
+                    <callout arearefs="properties5">
+                        <para>
+                            <literal>unique</literal> (optionnel - par défaut à <literal>false</literal>) :
+                            Indique qu'une contrainte d'unicité existe sur toutes les colonnes mappées de ce composant.
+                            </para>
+                    </callout>
+                </calloutlist>
+            </programlistingco>
+            <para>
+                Par exemple, si nous avons le mapping de <literal>&lt;properties&gt;</literal> suivant :
+            </para>
+            <programlisting><![CDATA[<class name="Person">
+    <id name="personNumber"/>
+    ...
+    <properties name="name" 
+            unique="true" update="false">
+        <property name="firstName"/>
+        <property name="initial"/>
+        <property name="lastName"/>
+    </properties>
+</class>]]></programlisting>
+            <para>
+                Alors nous pourrions avoir une association sur des données d'un ancien système (legacy) qui font référence 
+                à cette clef unique de la table <literal>Person</literal> au lieu de la clef primaire :
+            </para>
+            <programlisting><![CDATA[<many-to-one name="person" 
+         class="Person" property-ref="name">
+    <column name="firstName"/>
+    <column name="initial"/>
+    <column name="lastName"/>
+</many-to-one>]]></programlisting>
+            <para>
+                Nous ne recommandons pas l'utilisation de ce genre de chose en dehors du contexte de mapping de données héritées 
+                d'anciens systèmes.
+            </para>
+        </sect2>
+        <sect2 id="mapping-declaration-subclass" revision="4">
+            <title>subclass</title>
+            <para>
+                Pour finir, la persistance polymorphique nécessite la déclaration de chaque sous-classe de la classe persistante de base. 
+                pour la stratégie de mapping de type table-per-class-hierarchy, on utilise la déclaration 
+                <literal>&lt;subclass&gt;</literal>.    
+            </para>
+            <programlistingco>
+                <areaspec>
+                    <area id="subclass1" coords="2 55"/>
+                    <area id="subclass2" coords="3 55"/>
+                    <area id="subclass3" coords="4 55"/>
+                    <area id="subclass4" coords="5 55"/>
+                </areaspec>
+                <programlisting><![CDATA[<subclass
+        name="ClassName"
+        discriminator-value="discriminator_value"
+        proxy="ProxyInterface"
+        lazy="true|false"
+        dynamic-update="true|false"
+        dynamic-insert="true|false"
+        entity-name="EntityName"
+        node="element-name"
+        extends="SuperclassName">
+
+        <property .... />
+        .....
+</subclass>]]></programlisting>
+                <calloutlist>
+                    <callout arearefs="subclass1">
+                        <para>
+                            <literal>name</literal> : Le nom complet de la sous-classe.
+                        </para>
+                    </callout>
+                    <callout arearefs="subclass2">
+                        <para>
+                            <literal>discriminator-value</literal> (optionnel - par défaut le nom de la classe) : 
+                            une valeur qui distingue les différentes sous-classes.
+                        </para>
+                    </callout>
+                    <callout arearefs="subclass3">
+                        <para>
+                            <literal>proxy</literal> (optionnel) : Indique une classe ou interface à utiliser pour les chargements
+                            à la demande des proxies (lazy).
+                        </para>
+                    </callout>
+                    <callout arearefs="subclass4">
+                        <para>
+                            <literal>lazy</literal> (optionnel, par défaut à <literal>true</literal>) : Spécifier 
+                            <literal>lazy="false"</literal> désactive l'utilisation du chargement à la demande (lazy).
+                        </para>
+                    </callout>
+                </calloutlist>
+            </programlistingco>
+            <para>
+                Chaque sous-classe devrait déclarer ses propres propriétés persistantes et sous-classes.
+                Les propriétés <literal>&lt;version&gt;</literal> et <literal>&lt;id&gt;</literal> 
+                sont implicitement hérités de la classe de base. Chaque sous-classe dans une hiérarchie doit 
+                définir une unique <literal>discriminator-value</literal>. Si aucune n'est spécifiée, 
+                le nom complet de la classe Java est utilisé.
+            </para>
+            <para>
+                Pour plus d'infos sur le mapping d'héritage, voir <xref linkend="inheritance"/>.
+        </para>
+            <programlisting><![CDATA[
+<hibernate-mapping>
+    <subclass name="DomesticCat" extends="Cat" discriminator-value="D">
+         <property name="name" type="string"/>
+    </subclass>
+</hibernate-mapping>]]></programlisting>
+            <para>
+                Pour des informations sur les mappings d'héritage, voir <xref linkend="inheritance"/>.
+            </para>
+        </sect2>
+        <sect2 id="mapping-declaration-joinedsubclass" revision="3">
+            <title>joined-subclass</title>
+            <para>
+                Une autre façon possible de faire est la suivante, chaque sous-classe peut être mappée vers sa propre table (stratégie 
+                de mapping de type table-per-subclass). L'état hérité est récupéré en joignant la table de la super-classe.
+                L'élément <literal>&lt;joined-subclass&gt;</literal> est utilisé.
+            </para>
+            <programlistingco>
+                <areaspec>
+                    <area id="joinedsubclass1" coords="2 45"/>
+                    <area id="joinedsubclass2" coords="3 45"/>
+                    <area id="joinedsubclass3" coords="4 45"/>
+                    <area id="joinedsubclass4" coords="5 45"/>
+                </areaspec>
+                <programlisting><![CDATA[<joined-subclass
+        name="ClassName"
+        table="tablename"
+        proxy="ProxyInterface"
+        lazy="true|false"
+        dynamic-update="true|false"
+        dynamic-insert="true|false"
+        schema="schema"
+        catalog="catalog"
+        extends="SuperclassName"
+        persister="ClassName"
+        subselect="SQL expression"
+        entity-name="EntityName">
+
+        <key .... >
+
+        <property .... />
+        .....
+</joined-subclass>]]></programlisting>
+                <calloutlist>
+                    <callout arearefs="joinedsubclass1">
+                        <para>
+                            <literal>name</literal> : Le nom Java complet de la sous-classe.
+                        </para>
+                    </callout>
+                    <callout arearefs="joinedsubclass2">
+                        <para>
+                            <literal>table</literal> : Le nom de la table de la sous-classe.
+                        </para>
+                    </callout>
+                    <callout arearefs="joinedsubclass3">
+                        <para>
+                            <literal>proxy</literal> (optionnel) : Indique une classe ou interface pour le chargement différé des proxies.
+                        </para>
+                    </callout>
+                    <callout arearefs="joinedsubclass4">
+                        <para>
+                            <literal>lazy</literal> (optionnel, par défaut à <literal>true</literal>) : Indiquer 
+                            <literal>lazy="false"</literal> désactive l'utilisation du chargement à la demande.
+                         </para>
+                    </callout>
+                </calloutlist>
+            </programlistingco>
+            <para>
+                Aucune colonne discriminante n'est nécessaire pour cette stratégie de mapping. Cependant, 
+                chaque sous-classe doit déclarer une colonne de table contenant l'objet identifiant qui utilise l'élément 
+                <literal>&lt;key&gt;</literal>. Le mapping au début de ce chapitre serait ré-écrit ainsi :
+            </para>
+            <programlisting><![CDATA[<?xml version="1.0"?>
+<!DOCTYPE hibernate-mapping PUBLIC
+        "-//Hibernate/Hibernate Mapping DTD//EN"
+        "http://hibernate.sourceforge.net/hibernate-mapping-3.0.dtd">
+
+<hibernate-mapping package="eg">
+
+        <class name="Cat" table="CATS">
+                <id name="id" column="uid" type="long">
+                        <generator class="hilo"/>
+                </id>
+                <property name="birthdate" type="date"/>
+                <property name="color" not-null="true"/>
+                <property name="sex" not-null="true"/>
+                <property name="weight"/>
+                <many-to-one name="mate"/>
+                <set name="kittens">
+                        <key column="MOTHER"/>
+                        <one-to-many class="Cat"/>
+                </set>
+                <joined-subclass name="DomesticCat" table="DOMESTIC_CATS">
+                    <key column="CAT"/>
+                    <property name="name" type="string"/>
+                </joined-subclass>
+        </class>
+
+        <class name="eg.Dog">
+                <!-- mapping for Dog could go here -->
+        </class>
+
+</hibernate-mapping>]]></programlisting>
+            <para>
+                 Pour des informations sur les mappings d'héritage, voir <xref linkend="inheritance"/>.
+             </para>
+        </sect2>
+        <sect2 id="mapping-declaration-unionsubclass" revision="2">
+            <title>union-subclass</title>
+            <para>
+               Une troisième option est de seulement mapper vers des tables les classes concrètes 
+               d'une hiérarchie d'héritage, (stratégie de type table-per-concrete-class) où 
+               chaque table définit tous les états persistants de la classe, y compris les états hérités. 
+               Dans Hibernate il n'est absolument pas nécessaire de mapper explicitement de telles hiérarchies 
+               d'héritage. Vous pouvez simplement mapper chaque classe avec une déclaration <literal>&lt;class&gt;</literal> 
+               différente. Cependant, si vous souhaitez utiliser des associations polymorphiques (càd une association 
+               vers la superclasse de la hiérarchie), vous devez utiliser le mapping <literal>&lt;union-subclass&gt;</literal>.
+           </para>
+            <programlistingco>
+                <areaspec>
+                    <area id="unionsubclass1" coords="2 45"/>
+                    <area id="unionsubclass2" coords="3 45"/>
+                    <area id="unionsubclass3" coords="4 45"/>
+                    <area id="unionsubclass4" coords="5 45"/>
+                </areaspec>
+                <programlisting><![CDATA[<union-subclass
+        name="ClassName"
+        table="tablename"
+        proxy="ProxyInterface"
+        lazy="true|false"
+        dynamic-update="true|false"
+        dynamic-insert="true|false"
+        schema="schema"
+        catalog="catalog"
+        extends="SuperclassName"
+        abstract="true|false"
+        persister="ClassName"
+        subselect="SQL expression"
+        entity-name="EntityName">
+
+        <property .... />
+        .....
+</union-subclass>]]></programlisting>
+                <calloutlist>
+                    <callout arearefs="unionsubclass1">
+                        <para>
+                            <literal>name</literal> : Le nom Java complet de la sous-classe.
+                        </para>
+                    </callout>
+                    <callout arearefs="unionsubclass2">
+                        <para>
+                            <literal>table</literal> : nom de la table de la sous-classe.
+                        </para>
+                    </callout>
+                    <callout arearefs="unionsubclass3">
+                        <para>
+                            <literal>proxy</literal> (optionnel) : Indique une classe ou interface pour le chargement différé des proxies.
+                        </para>
+                    </callout>
+                    <callout arearefs="unionsubclass4">
+                        <para>
+                            <literal>lazy</literal> (optionnel, par défaut à <literal>true</literal>) : Indiquer 
+                            <literal>lazy="false"</literal> désactive l'utilisation du chargement à la demande.
+                         </para>
+
+                    </callout>
+                </calloutlist>
+            </programlistingco>
+            <para>
+                Aucune colonne discriminante ou colonne clef n'est requise pour cette stratégie de mapping.
+            </para>
+            <para>
+                Pour des informations sur les mappings d'héritage, voir <xref linkend="inheritance"/>.
+            </para>
+        </sect2>
+        <sect2 id="mapping-declaration-join" revision="3">
+            <title>join</title>
+            <para>
+                En utilisant l'élément <literal>&lt;join&gt;</literal>, il est possible de mapper 
+                des propriétés d'une classe sur plusieurs tables.
+            </para>
+            <programlistingco>
+                <areaspec>
+                    <area id="join1" coords="2 50"/>
+                    <area id="join2" coords="3 50"/>
+                    <area id="join3" coords="4 50"/>
+                    <area id="join4" coords="5 50"/>
+                    <area id="join5" coords="6 50"/>
+                    <area id="join6" coords="7 50"/>
+                </areaspec>
+                <programlisting><![CDATA[<join
+        table="tablename"
+        schema="owner"
+        catalog="catalog"
+        fetch="join|select"
+        inverse="true|false"
+        optionnel="true|false">
+        
+        <key ... />
+        
+        <property ... />
+        ...
+</join>]]></programlisting>
+                <calloutlist>
+                    <callout arearefs="join1">
+                        <para>
+                            <literal>table</literal> : Le nom de la table jointe.
+                        </para>
+                    </callout>
+                    <callout arearefs="join2">
+                        <para>
+                            <literal>schema</literal> (optionnel) : court-circuite le nom de schéma spécifié par l'élément de base 
+                            <literal>&lt;hibernate-mapping&gt;</literal>.
+                        </para>
+                    </callout>
+                    <callout arearefs="join3">
+                        <para>
+                            <literal>catalog</literal> (optionnel) : court-circuite le nom de catalogue spécifié par l'élément de base 
+                            <literal>&lt;hibernate-mapping&gt;</literal>.
+                        </para>
+                    </callout>
+                    <callout arearefs="join4">
+                        <para>
+                            <literal>fetch</literal> (optionnel - par défaut à <literal>join</literal>) :
+                            Si positionné à <literal>join</literal>, Hibernate utilisera une jointure interne pour charger
+                            une <literal>jointure</literal> définie par une classe ou ses super-classes et une jointure externe
+                            pour une <literal>&lt;jointure&gt;</literal> définie par une sous-classe.
+                            Si positionné à <literal>select</literal> alors Hibernate utilisera un select séquentiel 
+                            pour une <literal>&lt;jointure&gt;</literal> définie sur une sous-classe, qui ne sera délivrée que
+                            si une ligne se représente une instance de la sous-classe. Les jointures internes seront quand même 
+                            utilisées pour charger une <literal>&lt;jointure&gt;</literal> définie par une classe et ses super-classes.
+                        </para>
+                    </callout>
+                    <callout arearefs="join5">
+                        <para>
+                            <literal>inverse</literal> (optionnel - par défaut à <literal>false</literal>) :
+                            Si positionné à true, Hibernate n'essaiera pas d'insérer ou de mettre à jour les 
+                            propriétés définies par cette jointure.
+                        </para>
+                    </callout>
+                    <callout arearefs="join6">
+                        <para>
+                            <literal>optionnel</literal> (optionnel - par défaut à <literal>false</literal>) :
+                            Si positionné à true, Hibernate insèrera une ligne seulement si les propriétés définies 
+                            par cette jointure sont non-nulles et utilisera toujours une jointure externe pour charger les propriétés.
+                        </para>
+                    </callout>
+                </calloutlist>
+            </programlistingco>
+            <para>
+                Par exemple, les informations d'adresse pour une personne peuvent être mappées vers une table 
+                séparée (tout en préservant des sémantiques de type valeur pour toutes ses propriétés) :
+            </para>
+            <programlisting><![CDATA[<class name="Person"
+    table="PERSON">
+
+    <id name="id" column="PERSON_ID">...</id>
+
+    <join table="ADDRESS">
+        <key column="ADDRESS_ID"/>
+        <property name="address"/>
+        <property name="zip"/>
+        <property name="country"/>
+    </join>
+    ...]]></programlisting>
+            <para>
+                Cette fonctionnalité est souvent seulement utile pour les modèles de données 
+                hérités d'anciens systèmes (legacy), nous recommandons d'utiliser moins de tables que de classes 
+                et un modèle de domaine à granularité fine. Cependant, c'est utile 
+                pour passer d'une stratégie de mapping d'héritage à une autre dans une hiérarchie simple ainsi qu'il est 
+                expliqué plus tard.
+            </para>
+        </sect2>
+        <sect2 id="mapping-declaration-key">
+            <title>key</title>
+            <para>
+                Nous avons rencontré l'élément <literal>&lt;key&gt;</literal> à plusieurs reprises maintenant. 
+                Il apparaît partout que l'élément de mapping parent définit une jointure sur une nouvele table, et 
+                définit la clef étrangère dans la table jointe, ce qui référence la clef primaire de la table d'origine.
+            </para>
+            <programlistingco>
+                <areaspec>
+                    <area id="key1" coords="2 50"/>
+                    <area id="key2" coords="3 50"/>
+                    <area id="key3" coords="4 50"/>
+                    <area id="key4" coords="5 50"/>
+                    <area id="key5" coords="6 50"/>
+                    <area id="key6" coords="7 50"/>
+                </areaspec>
+                <programlisting><![CDATA[<key
+        column="columnname"
+        on-delete="noaction|cascade"
+        property-ref="propertyName"
+        not-null="true|false"
+        update="true|false"
+        unique="true|false"
+/>]]></programlisting>
+                <calloutlist>
+                    <callout arearefs="key1">
+                        <para>
+                            <literal>column</literal> (optionnel) : Le nom de la colonne de la clef étrangère
+                            Cela peut aussi être spécifié par l'élément(s) intégré(s) <literal>&lt;column&gt;</literal>.
+                        </para>
+                    </callout>
+                    <callout arearefs="key2">
+                        <para>
+                            <literal>on-delete</literal> (optionnel, par défaut à <literal>noaction</literal>) :
+                            Indique si la contrainte de clef étrangère possède la possibilité au niveau base de données 
+                            de suppression en cascade.
+                        </para>
+                    </callout>
+                    <callout arearefs="key3">
+                        <para>
+                            <literal>property-ref</literal> (optionnel) : Indique que la clef étrangère fait 
+                            référence à des colonnes qui ne sont pas la clef primaire de la table d'origine 
+                            (Pour les données de systèmes legacy).
+                        </para>
+                    </callout>
+                    <callout arearefs="key4">
+                        <para>
+                            <literal>not-null</literal> (optionnel) : Indique que les colonnes des clefs étrangères ne 
+                            peuvent pas être nulles (c'est implicite si la clef étrangère fait partie de la clef primaire).
+                        </para>
+                    </callout>
+                    <callout arearefs="key5">
+                        <para>
+                            <literal>update</literal> (optionnel) : Indique que la clef étrangère ne devrait jamais être mise à jour 
+                            (implicite si celle-ci fait partie de la clef primaire).
+                        </para>
+                    </callout>
+                    <callout arearefs="key6">
+                        <para>
+                            <literal>unique</literal> (optionnel) : Indique que la clef étrangère doit posséder une contrainte 
+                            d'unicité (implicite si la clef étrangère est aussi la clef primaire).
+                        </para>
+                    </callout>
+                </calloutlist>
+            </programlistingco>
+            <para>
+                Nous recommandons pour les systèmes où les suppressions doivent être performantes de définir toutes 
+                les clefs <literal>on-delete="cascade"</literal>, ainsi Hibernate utilisera une contrainte 
+                <literal>ON CASCADE DELETE</literal> au niveau base de données, plutôt que de nombreux
+                <literal>DELETE</literal> individuels. Attention, cette fonctionnalité court-circuite la stratégie 
+                habituelle de verrou optimiste pour les données versionnées.
+            </para>
+            <para>
+                Les attributs <literal>not-null</literal> et <literal>update</literal> sont utiles pour 
+                mapper une association one-to-many unidirectionnelle. Si vous mappez un one-to-many unidirectionnel 
+                vers une clef étrangère non nulle, vous <emphasis>devez</emphasis> déclarer la colonne de la clef 
+                en utilisant <literal>&lt;key not-null="true"&gt;</literal>.
+            </para>
+        </sect2>
+        <sect2 id="mapping-column" revision="4">
+            <title>éléments column et formula</title>
+            <para>
+               Tout élément de mapping qui accepte un attribut <literal>column</literal> acceptera alternativement 
+               un sous-élément <literal>&lt;column&gt;</literal>. De façon identique, <literal>&lt;formula&gt;</literal> 
+               est une alternative à l'attribut <literal>formula</literal>.
+           </para>
+            <programlisting><![CDATA[<column
+        name="column_name"
+        length="N"
+        precision="N"
+        scale="N"
+        not-null="true|false"
+        unique="true|false"
+        unique-key="multicolumn_unique_key_name"
+        index="index_name"
+        sql-type="sql_type_name"
+        check="SQL expression"/>]]></programlisting>
+            <programlisting><![CDATA[<formula>SQL expression</formula>]]></programlisting>
+            <para>
+                Les attributs <literal>column</literal> et <literal>formula</literal> peuvent même être combinés 
+                au sein d'une même propriété ou mapping d'association pour exprimer, par exemple, des conditions 
+                de jointure exotiques.
+            </para>
+            <programlisting><![CDATA[<many-to-one name="homeAddress" class="Address"
+        insert="false" update="false">
+    <column name="person_id" not-null="true" length="10"/>
+    <formula>'MAILING'</formula>
+</many-to-one>]]></programlisting>
+        </sect2>
+        <sect2 id="mapping-declaration-import">
+            <title>import</title>
+            <para>
+                Supposez que votre application possède deux classes persistantes du même nom, et vous ne voulez pas préciser 
+                le nom Java complet (packages inclus) dans les queries Hibernate. Les classes peuvent alors être "importées" 
+                explicitement plutôt que de compter sur <literal>auto-import="true"</literal>.Vous pouvez même importer 
+                des classes et interfaces qui ne sont pas mappées explicitement.
+            </para>
+            <programlisting><![CDATA[<import class="java.lang.Object" rename="Universe"/>]]></programlisting>
+            <programlistingco>
+                <areaspec>
+                    <area id="import1" coords="2 40"/>
+                    <area id="import2" coords="3 40"/>
+                </areaspec>
+                <programlisting><![CDATA[<import
+        class="ClassName"
+        rename="ShortName"
+/>]]></programlisting>
+                <calloutlist>
+                    <callout arearefs="import1">
+                        <para>
+                            <literal>class</literal> : Nom Java complet de la classe.
+                        </para>
+                    </callout>
+                    <callout arearefs="import2">
+                        <para>
+                            <literal>rename</literal> (optionnel - par défaut vaut le nom de la classe Java (sans package)) :
+                            Nom pouvant être utilisé dans le langage de requête.
+                        </para>
+                    </callout>
+                </calloutlist>
+            </programlistingco>
+        </sect2>
+        <sect2 id="mapping-types-anymapping" revision="2">
+            <title>any</title>
+            <para>
+                Il existe encore un type de mapping de propriété. L'élément de mapping <literal>&lt;any&gt;</literal> 
+                définit une association polymorphique vers des classes de tables multiples. Ce type de mapping requiert 
+                toujours plus d'une colonne. La première colonne contient le type de l'entité associée. Les colonnes 
+                restantes contiennent l'identifiant. il est impossible de spécifier une contrainte de clef étrangère 
+                pour ce type d'association, donc ce n'est certainement pas considéré comme le moyen habituel de mapper 
+                des associations (polymorphiques). Vous devriez utiliser cela uniquement dans des cas particuliers 
+                (par exemple des logs d'audit, des données de session utilisateur, etc...).
+            </para>
+            <para>
+                 L'attribut <literal>meta-type</literal> permet à l'application de spécifier un type personnalisé qui mappe 
+                 des valeurs de colonnes de le base de données sur des classes persistantes qui ont un attribut identifiant 
+                 du type spécifié par <literal>id-type</literal>. Vous devez spécifier le mapping à partir de valeurs du 
+                 méta-type sur les noms des classes.
+            </para>
+            <programlisting><![CDATA[<any name="being" id-type="long" meta-type="string">
+    <meta-value value="TBL_ANIMAL" class="Animal"/>
+    <meta-value value="TBL_HUMAN" class="Human"/>
+    <meta-value value="TBL_ALIEN" class="Alien"/>
+    <column name="table_name"/>
+    <column name="id"/>
+</any>]]></programlisting>
+            <programlistingco>
+                <areaspec>
+                    <area id="any1" coords="2 50"/>
+                    <area id="any2" coords="3 50"/>
+                    <area id="any3" coords="4 50"/>
+                    <area id="any4" coords="5 50"/>
+                    <area id="any5" coords="6 50"/>
+                    <area id="any6" coords="7 50"/>
+                </areaspec>
+                <programlisting><![CDATA[<any
+        name="propertyName"
+        id-type="idtypename"
+        meta-type="metatypename"
+        cascade="cascade_style"
+        access="field|property|ClassName"
+        optimistic-lock="true|false"
+>
+        <meta-value ... />
+        <meta-value ... />
+        .....
+        <column .... />
+        <column .... />
+        .....
+</any>]]></programlisting>
+                <calloutlist>
+                    <callout arearefs="any1">
+                        <para>
+                            <literal>name</literal> : le nom de la propriété.
+                        </para>
+                    </callout>
+                    <callout arearefs="any2">
+                        <para>
+                            <literal>id-type</literal> : le type identifiant.
+                        </para>
+                    </callout>
+                    <callout arearefs="any3">
+                        <para>
+                            <literal>meta-type</literal> (optionnel - par défaut à <literal>string</literal>) : 
+                            Tout type permis pour un mapping par discriminateur.
+                        </para>
+                    </callout>
+                    <callout arearefs="any4">
+                        <para>
+                            <literal>cascade</literal> (optionnel - par défaut à <literal>none</literal>) : 
+                            le style de cascade.
+                        </para>
+                    </callout>
+                    <callout arearefs="any5">
+                        <para>
+                            <literal>access</literal> (optionnel - par défaut à <literal>property</literal>) : La stratégie 
+                            à utiliser par Hibernate pour accéder à cette propriété.
+                        </para>
+                    </callout>
+                    <callout arearefs="any6">
+                        <para>
+                            <literal>optimistic-lock</literal> (optionnel - par défaut à <literal>true</literal>) : 
+                            Indique que les mises à jour sur cette propriété nécessitent ou non l'acquisition d'un 
+                            verrou optimiste. En d'autres termes, définit si un incrément de version doit avoir lieu 
+                            quand cette propriété est marquée dirty.
+                        </para>
+                    </callout>
+                </calloutlist>
+            </programlistingco>
+        </sect2>
+    </sect1>
+    <sect1 id="mapping-types">
+        <title>Hibernate Types</title>
+        <sect2 id="mapping-types-entitiesvalues" revision="1">
+            <title>Entités et valeurs</title>
+            <para>
+                Pour comprendre le comportement des différents objets Java par rapport au service 
+                de persistance, nous avons besoin de les classer en deux groupes :
+            </para>
+            <para>
+                Une <emphasis>entité</emphasis> existe indépendamment de tout autre objet possédant 
+                une référence vers l'entité. Comparez cela avec le modèle Java habituel où un objet 
+                est supprimé par le garbage collector dès qu'il n'est plus référencé. Les entités 
+                doivent être explicitement enregistrées et supprimées (sauf dans les cas où 
+                sauvegardes et suppressions sont <emphasis>cascadées</emphasis> d'une entité mère 
+                vers ses enfants). C'est différent du modèle ODMG de persistance par 
+                atteignabilité - et correspond mieux à la façon dont les objets sont 
+                habituellement utilisés dans des grands systèmes. Les entités permettent les références 
+                circulaires et partagées. Elles peuvent aussi être versionnées.
+            </para>
+            <para>
+                L'état persistant d'une entité consiste en des références vers d'autres entités et 
+                instances de types <emphasis>valeurs</emphasis>. Ces valeurs sont des types primitifs, 
+                des collections (et non le contenu d'une collection), des composants de certains objets 
+                immuables. Contrairement aux entités, les valeurs (et en particulier les collections et 
+                composants) <emphasis>sont</emphasis> persistés par atteignabiliité. Comme les 
+                valeurs (et types primitifs) sont persistés et supprimés avec l'entité qui les contient, 
+                ils ne peuvent pas posséder leurs propres versions. Les valeurs n'ont pas d'identité 
+                indépendantes, ainsi elles ne peuvent pas être partagées par deux entités ou collections.
+            </para>
+            <para>
+                Jusqu'à présent nous avons utilisé le terme "classe persistante" pour parler d'entités. 
+                Nous allons continuer à faire ainsi. Cependant, au sens strict, toutes 
+                les classes définies par un utilisateur possédant un état persistant ne sont pas des 
+                entités. Un <emphasis>composant</emphasis> est une classe définie par un utilisateur 
+                avec les caractéristiques d'une valeur. Une propriété Java de type <literal>java.lang.String</literal>
+                a aussi les caractéristiques d'une valeur. 
+                
+                <!-- FIXME Baptiste MATHUS : J'ai remis le texte anglais pour que si la version est publiée
+                comme ça, au moins le lecteur puisse essayer lui aussi de comprendre la version anglaise... -->
+                
+                Given this definition, we can say that all types (classes) provided
+                by the JDK have value type semantics in Java, while user-defined types may
+                be mapped with entity or value type semantics. This decision is up to the
+                application developer. A good hint for an entity class in a domain model are
+                shared references to a single instance of that class, while composition or
+                aggregation usually translates to a value type.
+            </para>
+            <para>
+                Nous nous pencherons sur ces deux concepts tout au long de la documentation.
+            </para>
+            <para>
+                Le défi est de mapper les type Javas (et la définition des développeurs des 
+                entités et valeurs types) sur les types du SQL ou des bases de données. Le pont 
+                entre les deux systèmes est proposé par Hibernate : pour les entités nous utilisons 
+                <literal>&lt;class&gt;</literal>, <literal>&lt;subclass&gt;</literal> et ainsi de suite.
+                Pour les types valeurs nous utilisons <literal>&lt;property&gt;</literal>,
+                <literal>&lt;component&gt;</literal>, etc., habituellement avec un attribut <literal>type</literal>. 
+                La valeur de cet attribut est le nom d'un <emphasis>type de mapping</emphasis> Hibernate. 
+                Hibernate propose de base de nombreux mappings (pour les types de valeurs standards du JDK). 
+                Vous pouvez écrire vos propres types de mappings et implémenter aussi vos propres stratégies 
+                de conversion, nous le verrons plus tard.
+            </para>
+            <para>
+                Tous les types proposés de base par Hibernate à part les collections autorisent la valeur null.
+            </para>
+        </sect2>
+        <sect2 id="mapping-types-basictypes" revision="3">
+            <title>Basic value types</title>
+            <para>
+                Les <emphasis>types basiques de mapping</emphasis> proposés de base peuvent grossièrement être 
+                rangés dans les catégories suivantes :
+                <variablelist>
+                    <varlistentry>
+                        <term>
+                            <literal>integer, long, short, float, double, character, byte,
+                            boolean, yes_no, true_false</literal>
+                        </term>
+                        <listitem>
+                            <para>
+                                Les mappings de type des primitives Java ou leurs classes wrappers (ex: Integer 
+                                pour int) vers les types SQL (propriétaires) appropriés. <literal>boolean, 
+                                yes_no</literal>et <literal>true_false</literal> sont tous des alternatives 
+                                pour les types Java <literal>boolean</literal> ou <literal>java.lang.Boolean</literal>.
+                            </para>
+                        </listitem>
+                    </varlistentry>
+                    <varlistentry>
+                        <term>
+                            <literal>string</literal>
+                        </term>
+                        <listitem>
+                            <para>
+                                Mapping de type de <literal>java.lang.String</literal> vers
+                                <literal>VARCHAR</literal> (ou le <literal>VARCHAR2</literal> Oracle).
+                            </para>
+                        </listitem>
+                    </varlistentry>
+                    <varlistentry>
+                        <term>
+                            <literal>date, time, timestamp</literal>
+                        </term>
+                        <listitem>
+                            <para>
+                                Mappings de type pour <literal>java.util.Date</literal> et ses sous-classes  
+                                vers les types SQL <literal>DATE</literal>, <literal>TIME</literal> et
+                                <literal>TIMESTAMP</literal> (ou équivalent).
+                            </para>
+                        </listitem>
+                    </varlistentry>
+                    <varlistentry>
+                        <term>
+                            <literal>calendar, calendar_date</literal>
+                        </term>
+                        <listitem>
+                            <para>
+                                Mappings de type pour <literal>java.util.Calendar</literal> vers les types SQL 
+                                <literal>TIMESTAMP</literal> et <literal>DATE</literal>
+                                (ou équivalent).
+                            </para>
+                        </listitem>
+                    </varlistentry>
+                    <varlistentry>
+                        <term>
+                            <literal>big_decimal, big_integer</literal>
+                        </term>
+                        <listitem>
+                            <para>
+                                Mappings de type pour <literal>java.math.BigDecimal</literal> et
+                                <literal>java.math.BigInteger</literal> vers <literal>NUMERIC</literal> 
+                                (ou le <literal>NUMBER</literal> Oracle).
+                            </para>
+                        </listitem>
+                    </varlistentry>
+                    <varlistentry>
+                        <term>
+                            <literal>locale, timezone, currency</literal>
+                        </term>
+                        <listitem>
+                            <para>
+                                Mappings de type pour <literal>java.util.Locale</literal>,
+                                <literal>java.util.TimeZone</literal> et 
+                                <literal>java.util.Currency</literal> 
+                                vers <literal>VARCHAR</literal> (ou le <literal>VARCHAR2</literal> Oracle).
+                                Les instances de <literal>Locale</literal> et <literal>Currency</literal> sont 
+                                mappées sur leurs codes ISO. Les instances de <literal>TimeZone</literal> sont
+                                mappées sur leur <literal>ID</literal>.
+                            </para>
+                        </listitem>
+                    </varlistentry>
+                    <varlistentry>
+                        <term>
+                            <literal>class</literal>
+                        </term>
+                        <listitem>
+                            <para>
+                                Un type de mapping pour <literal>java.lang.Class</literal> vers
+                                <literal>VARCHAR</literal> (ou le <literal>VARCHAR2</literal> Oracle).
+                                Un objet <literal>Class</literal> est mappé sur son nom Java complet.
+                            </para>
+                        </listitem>
+                    </varlistentry>
+                    <varlistentry>
+                        <term>
+                            <literal>binary</literal>
+                        </term>
+                        <listitem>
+                            <para>
+                                Mappe les tableaux de bytes vers le type binaire SQL approprié.
+                            </para>
+                        </listitem>
+                    </varlistentry>
+                    <varlistentry>
+                        <term>
+                            <literal>text</literal>
+                        </term>
+                        <listitem>
+                            <para>
+                                Mappe les longues chaînes de caractères Java vers les types SQL 
+                                <literal>CLOB</literal> ou <literal>TEXT</literal>.
+                            </para>
+                        </listitem>
+                    </varlistentry>
+                    <varlistentry>
+                        <term>
+                            <literal>serializable</literal>
+                        </term>
+                        <listitem>
+                            <para>
+                                Mappe les types Java sérialisables vers le type SQL binaire approprié. Vous pouvez 
+                                aussi indiquer le type Hibernate <literal>serializable</literal> avec le nom 
+                                d'une classe Java sérialisable ou une interface qui ne soit pas par défaut un type de base.
+                            </para>
+                        </listitem>
+                    </varlistentry>
+                    <varlistentry>
+                        <term>
+                            <literal>clob, blob</literal>
+                        </term>
+                        <listitem>
+                            <para>
+                                Mappings de type pour les classes JDBC <literal>java.sql.Clob</literal> and
+                                <literal>java.sql.Blob</literal>. Ces types peuvent ne pas convenir pour certaines 
+                                applications car un objet blob ou clob peut ne pas être réutilisable en dehors 
+                                d'une transaction (de plus l'implémentation par les pilotes est moyennement bonne).
+                           </para>
+                        </listitem>
+                    </varlistentry>
+                    <varlistentry>
+                        <term>
+                            <literal>imm_date, imm_time, imm_timestamp, imm_calendar, imm_calendar_date,
+                            imm_serializable, imm_binary</literal>
+                        </term>
+                        <listitem>
+                            <para>
+                                Mappings de type pour ceux qui sont habituellement modifiable, pour lesquels
+                                Hibernate effectue certains optimisations convenant seulement aux types Java immuables,
+                                et l'application les traite comme immuable. 
+                                Par exemple, vous ne devriez pas appeler <literal>Date.setTime()</literal> sur une instance
+                                mappée sur un <literal>imm_timestamp</literal>. Pour changer la valeur
+                                de la propriété, et faire que cette modification soit persistée, l'application
+                                doit assigner un nouvel (non identique) objet à la propriété.
+                            </para>
+                        </listitem>
+                    </varlistentry>
+                </variablelist>
+            </para>
+            <para>
+                Les identifiants uniques des entités et collections peuvent être de n'importe quel type de base excepté 
+                <literal>binary</literal>, <literal>blob</literal> et <literal>clob</literal> (les identifiants 
+                composites sont aussi permis, voir plus bas).
+            </para>
+            <para>
+                Les types de base des valeurs ont des <literal>Type</literal> constants correspondants définis 
+                dans <literal>org.hibernate.Hibernate</literal>. Par exemple, <literal>Hibernate.STRING</literal>
+                représenté le type <literal>string</literal>.
+            </para>
+        </sect2>
+        <sect2 id="mapping-types-custom" revision="2">
+            <title>Types de valeur définis par l'utilisateur</title>
+            <para>
+                Il est assez facile pour les développeurs de créer leurs propres types de valeurs. Par exemple, 
+                vous pourriez vouloir persister des propriétés du type <literal>java.lang.BigInteger</literal>
+                dans des colonnnes <literal>VARCHAR</literal>. Hibernate ne procure pas par défaut un type pour cela. 
+                Mais les types que vous pouvez créer ne se limitent pas à mapper des propriétés (ou élément collection) 
+                à une simple colonne d'une table. Donc, par exemple, vous pourriez avoir une propriété Java 
+                <literal>getName()</literal>/<literal>setName()</literal> de type 
+                <literal>java.lang.String</literal> persistée dans les colonnes  
+                <literal>FIRST_NAME</literal>, <literal>INITIAL</literal>, <literal>SURNAME</literal>.
+            </para>
+            <para>
+                Pour implémenter votre propre type, vous pouvez soit implémenter <literal>org.hibernate.UserType</literal> 
+                soit <literal>org.hibernate.CompositeUserType</literal> et déclarer des propriétés utilisant des 
+                noms de classes complets du type. Regardez <literal>org.hibernate.test.DoubleStringType</literal> 
+                pour voir ce qu'il est possible de faire.
+            </para>
+            <programlisting><![CDATA[<property name="twoStrings" type="org.hibernate.test.DoubleStringType">
+    <column name="first_string"/>
+    <column name="second_string"/>
+</property>]]></programlisting>
+            <para>
+                Remarquez l'utilisation des tags <literal>&lt;column&gt;</literal> pour mapper une propriété sur des colonnes 
+                multiples.
+            </para>
+            <para>
+                Les interfaces <literal>CompositeUserType</literal>, <literal>EnhancedUserType</literal>,
+                <literal>UserCollectionType</literal>, et <literal>UserVersionType</literal> permettent des utilisations 
+                plus spécialisées.
+            </para>
+            <para>
+                Vous pouvez même donner des paramètres en indiquant <literal>UserType</literal> dans le fichier 
+                de mapping ; Pour cela, votre <literal>UserType</literal> doit implémenter l'interface 
+                <literal>org.hibernate.usertype.ParameterizedType</literal>. Pour spécifier des paramètres dans 
+                votre type propre, vous pouvez utiliser l'élément <literal>&lt;type&gt;</literal> dans vos fichiers de mapping.
+            </para>
+            <programlisting><![CDATA[<property name="priority">
+    <type name="com.mycompany.usertypes.DefaultValueIntegerType">
+        <param name="default">0</param>
+    </type>
+</property>]]></programlisting>
+            <para>
+                Le <literal>UserType</literal> permet maintenant de récupérer la valeur pour le paramètre nommé 
+                <literal>default</literal> à partir de l'objet <literal>Properties</literal> qui lui est passé.
+            </para>
+            <para>
+                Si vous utilisez fréquemment un <literal>UserType</literal>, cela peut être utile de lui définir un 
+                nom plus court. Vous pouvez faire cela en utilisant l'élément <literal>&lt;typedef&gt;</literal>. 
+                Les typedefs permettent d'assigner un nom à votre type propre et peuvent aussi contenir une liste de 
+                valeurs de paramètres par défaut si ce type est paramétré.
+            </para>
+            <programlisting><![CDATA[<typedef class="com.mycompany.usertypes.DefaultValueIntegerType" name="default_zero">
+    <param name="default">0</param>
+</typedef>]]></programlisting>
+            <programlisting><![CDATA[<property name="priority" type="default_zero"/>]]></programlisting>
+            <para>
+                Il est aussi possible de redéfinir les paramètres par défaut du typedef au cas par cas en 
+                utilisant des paramètres type sur le mapping de la propriété. 
+            </para>
+            <para>
+                Bien que le fait que Hibernate propose de base une riche variété de types, et qu'il supporte les composants 
+                signifie que vous aurez très rarement <emphasis>besoin</emphasis> d'utiliser un nouveau type propre, 
+                il est néanmoins de bonne pratique d'utiliser des types propres pour les classes (non entités) qui 
+                apparaissent fréquemment dans votre application. Par exemple une classe <literal>MonetaryAmount</literal> 
+                est un bon candidat pour un <literal>CompositeUserType</literal> même s'il pourrait facilement 
+                être mappé comme un composant. Une motivation pour cela est l'abstraction. Avec un type propre 
+                vos documents de mapping sont à l'abri des changements futurs dans votre façon de représenter des 
+                valeurs monétaires.
+            </para>
+        </sect2>
+    </sect1>
+    
+        <sect1 id="mapping-entityname">
+        <title>Mapper une classe plus d'une fois</title>
+        <para>
+            Il est possible de proposer plus d'un mapping par classe persistante. Dans ce cas, vous
+            devez spécifier un <emphasis>nom d'entité</emphasis> pour lever l'ambiguité entre les instances
+            des entités mappées (par défaut, le nom de l'entité est celui de la classe). Hibernate
+            vous permet de spécifier le nom de l'entité lorsque vous utilisez des objets persistants, lorsque
+            vous écrivez des requêtes ou quand vous mappez des associations vers les entités nommées.
+        </para>
+        
+        <programlisting><![CDATA[<class name="Contract" table="Contracts" 
+        entity-name="CurrentContract">
+    ...
+    <set name="history" inverse="true" 
+            order-by="effectiveEndDate desc">
+        <key column="currentContractId"/>
+        <one-to-many entity-name="HistoricalContract"/>
+    </set>
+</class>
+
+<class name="Contract" table="ContractHistory" 
+        entity-name="HistoricalContract">
+    ...
+    <many-to-one name="currentContract" 
+            column="currentContractId" 
+            entity-name="CurrentContract"/>
+</class>]]></programlisting>
+
+        <para>
+            Remarquez comment les associations sont désormais spécifiées en utilisant
+            <literal>entity-name</literal> au lieu de <literal>class</literal>.
+        </para>
+
+    </sect1>
+    
+    <sect1 id="mapping-quotedidentifiers">
+        <title>SQL quoted identifiers</title>
+        <para>
+            Vous pouvez forcer Hibernate à mettre un identifiant entre quotes dans le SQL généré en mettant le nom 
+            de la table ou de la colonne entre backticks dans le 
+            document de mapping. Hibernate utilisera les bons styles de quotes pour le <literal>Dialect</literal> SQL 
+            (habituellement des doubles quotes, mais des parenthèses pour SQL server et des backticks pour MySQL).
+        </para>
+        <programlisting><![CDATA[<class name="LineItem" table="`Line Item`">
+    <id name="id" column="`Item Id`"/><generator class="assigned"/></id>
+    <property name="itemNumber" column="`Item #`"/>
+    ...
+</class>]]></programlisting>
+    </sect1>
+    <sect1 id="mapping-alternatives">
+        <title>alternatives Metadata</title>
+        <para>
+            XML ne convient pas à tout le monde, il y a donc des moyens alternatifs pour définir des metatda 
+            de mappings O/R dans Hibernate.
+        </para>
+        <sect2 id="mapping-xdoclet">
+            <title>utilisation de XDoclet</title>
+            <para>
+                De nombreux utilisateurs de Hibernate préfèrent embarquer les informations de mappings 
+                directement au sein du code source en utilisant les tags XDoclet <literal>@hibernate.tags</literal>. 
+                Nous ne couvrons pas cette approche dans ce document cependant, puisque c'est considéré comme faisant partie 
+                de XDoclet. Cependant, nous présentons l'exemple suivant de la classe <literal>Cat</literal> avec 
+                des mappings XDoclet.
+        </para>
+            <programlisting><![CDATA[package eg;
+import java.util.Set;
+import java.util.Date;
+
+/**
+ * @hibernate.class
+ *  table="CATS"
+ */
+public class Cat {
+    private Long id; // identifier
+    private Date birthdate;
+    private Cat mother;
+    private Set kittens
+    private Color color;
+    private char sex;
+    private float weight;
+
+    /*
+     * @hibernate.id
+     *  generator-class="native"
+     *  column="CAT_ID"
+     */
+    public Long getId() {
+        return id;
+    }
+    private void setId(Long id) {
+        this.id=id;
+    }
+
+    /**
+     * @hibernate.many-to-one
+     *  column="PARENT_ID"
+     */
+    public Cat getMother() {
+        return mother;
+    }
+    void setMother(Cat mother) {
+        this.mother = mother;
+    }
+
+    /**
+     * @hibernate.property
+     *  column="BIRTH_DATE"
+     */
+    public Date getBirthdate() {
+        return birthdate;
+    }
+    void setBirthdate(Date date) {
+        birthdate = date;
+    }
+    /**
+     * @hibernate.property
+     *  column="WEIGHT"
+     */
+    public float getWeight() {
+        return weight;
+    }
+    void setWeight(float weight) {
+        this.weight = weight;
+    }
+
+    /**
+     * @hibernate.property
+     *  column="COLOR"
+     *  not-null="true"
+     */
+    public Color getColor() {
+        return color;
+    }
+    void setColor(Color color) {
+        this.color = color;
+    }
+    /**
+     * @hibernate.set
+     *  inverse="true"
+     *  order-by="BIRTH_DATE"
+     * @hibernate.collection-key
+     *  column="PARENT_ID"
+     * @hibernate.collection-one-to-many
+     */
+    public Set getKittens() {
+        return kittens;
+    }
+    void setKittens(Set kittens) {
+        this.kittens = kittens;
+    }
+    // addKitten not needed by Hibernate
+    public void addKitten(Cat kitten) {
+        kittens.add(kitten);
+    }
+
+    /**
+     * @hibernate.property
+     *  column="SEX"
+     *  not-null="true"
+     *  update="false"
+     */
+    public char getSex() {
+        return sex;
+    }
+    void setSex(char sex) {
+        this.sex=sex;
+    }
+}]]></programlisting>
+            <para>
+            Voyez le site web de Hibernate pour plus d'exemples sur XDoclet et Hibernate.
+        </para>
+        </sect2>
+        <sect2 id="mapping-annotations" revision="2">
+            <title>Utilisation des annotations JDK 5.0</title>
+            <para>
+                Le JDK 5.0 introduit des annotations proches de celles de XDoclet au niveau java, qui sont 
+                type-safe et vérifiées à la compilation. Ce mécanisme est plus puissant que XDoclet et mieux 
+                supporté par les outils et IDE. IntelliJ IDEA, par exemple, supporte l'auto-complétion et le 
+                surlignement syntaxique des annotations JDK 5.0. La nouvelle révision des spécifications des EJB 
+                (JSR-220) utilise les annotations JDK 5.0 comme mécanisme primaire pour les meta-données des beans entités. 
+                Hibernate3 implémente l'<literal>EntityManager</literal> de la JSR-220 (API de persistance), 
+                le support du mapping de meta-données est disponible via le package <emphasis>Hibernate Annotations</emphasis>, 
+                en tant que module séparé à télécharger. EJB3 (JSR-220) et les métadata Hibernate3 sont supportés.
+             </para>
+            <para>
+                Ceci est un exemple d'une classe POJO annotée comme un EJB entité :
+            </para>
+            <programlisting><![CDATA[@Entity(access = AccessType.FIELD)
+public class Customer implements Serializable {
+
+    @Id;
+    Long id;
+
+    String firstName;
+    String lastName;
+    Date birthday;
+
+    @Transient
+    Integer age;
+
+    @Embedded
+    private Address homeAddress;
+
+    @OneToMany(cascade=CascadeType.ALL)
+    @JoinColumn(name="CUSTOMER_ID")
+    Set<Order> orders;
+
+    // Getter/setter and business methods
+}]]></programlisting>
+            <para>
+                Notez que le support des annotations JDK 5.0 (et de la JSR-220) est encore en cours et n'est pas terminé.
+                Référez vous au module Hibernate Annotation pour plus de détails.
+            </para>
+        </sect2>
+    </sect1>
+    
+    <sect1 id="mapping-generated" revision="1">
+        <title>Propriétés générées</title>
+        <para>
+            Les propriétés générées sont des propriétés dont les valeurs sont générées par
+            la base de données. Typiquement, les applications Hibernate avaient besoin d'invoquer
+            <literal>refresh</literal> sur les instances qui contenaient des propriétés pour lesquelles
+            la base de données générait des valeurs. Marquer les propriétés comme générées permet à
+            l'application de déléguer cette responsabilité à Hibernate. Principalement, à chaque fois
+            qu'Hibernate réalise une insertion ou une mise à jour en base de données pour une entité
+            marquée comme telle, cela provoque immédiatement un select pour récupérer les valeurs générées.
+        </para>
+        <para>
+            Les propriétés marquées comme générées doivent de plus ne pas être insérables et modifiables 
+            Seuls <xref linkend="mapping-declaration-version">versions</xref>,
+            <xref linkend="mapping-declaration-timestamp">timestamps</xref>, et
+            <xref linkend="mapping-declaration-property">simple properties</xref> peuvent être marqués comme
+            générées.
+        </para>
+        <para>
+            <literal>never</literal> (par défaut) - indique la valeur de la propriété n'est pas générée
+            dans la base de données.
+        </para>
+        <para>
+            <literal>insert</literal> - indique que la valeur de la propriété donnée est
+            générée à l'insertion mais pas lors des futures mises à jour de l'enregistrement.
+            Les colonnes de type "date de création" sont le cas d'utilisation typique de cette option.
+            Notez que même les propriétés <xref linkend="mapping-declaration-version">version</xref> et
+            <xref linkend="mapping-declaration-timestamp">timestamp</xref> peuvent être
+            déclarées comme générées, cette option n'est pas disponible à cet endroit...
+        </para>
+        <para>
+            <literal>always</literal> - indique que la valeur de la propriété est générée à l'insert 
+            comme aux updates.
+        </para>
+        
+    </sect1>
+
+    <sect1 id="mapping-database-object">
+        <title>Objets auxiliaires de la base de données</title>
+        <para>
+            Permettent les ordres CREATE et DROP d'objets arbitraire de la base de donnéées, en conjonction avec
+            les outils Hibernate d'évolutions de schéma, pour permettre de définir complètement
+            un schéma utilisateur au sein des fichiers de mapping Hibernate. Bien que conçu spécifiquement
+            pour créer et supprimer des objets tels que des triggers et des procédures stockées,
+            ou toute commande pouvant être exécutée via une méthode de <literal>java.sql.Statement.execute()</literal>
+            (ALTERs, INSERTS, etc). Il y a principalement deux modes pour définir les objets auxiliaires de base de données...
+        </para>
+        <para>
+            Le premier mode est de lister explicitement les commandes CREATE et DROP dans le fichier
+            de mapping:
+        </para>
+        <programlisting><![CDATA[<hibernate-mapping>
+    ...
+    <database-object>
+        <create>CREATE TRIGGER my_trigger ...</create>
+        <drop>DROP TRIGGER my_trigger</drop>
+    </database-object>
+</hibernate-mapping>]]></programlisting>
+        <para>
+            Le second mode est de fournir une classe particulière qui connait comment construire
+            les commandes CREATE et DROP. Cette classe particulière doit implémenter l'interface
+            <literal>org.hibernate.mapping.AuxiliaryDatabaseObject</literal>.
+        </para>
+        <programlisting><![CDATA[<hibernate-mapping>
+    ...
+    <database-object>
+        <definition class="MyTriggerDefinition"/>
+    </database-object>
+</hibernate-mapping>]]></programlisting>
+        <para>
+            Additionnellement, ces objets de base de données peuvent être optionnellement traités
+            selon l'utilisation de dialectes particuliers..
+        </para>
+        <programlisting><![CDATA[<hibernate-mapping>
+    ...
+    <database-object>
+        <definition class="MyTriggerDefinition"/>
+        <dialect-scope name="org.hibernate.dialect.Oracle9Dialect"/>
+        <dialect-scope name="org.hibernate.dialect.OracleDialect"/>
+    </database-object>
+</hibernate-mapping>]]></programlisting>
+    </sect1>
+</chapter>

Copied: core/trunk/documentation/manual/fr-FR/src/main/docbook/content/batch.xml (from rev 14070, core/trunk/documentation/manual/fr-FR/src/main/docbook/modules/batch.xml)
===================================================================
--- core/trunk/documentation/manual/fr-FR/src/main/docbook/content/batch.xml	                        (rev 0)
+++ core/trunk/documentation/manual/fr-FR/src/main/docbook/content/batch.xml	2007-10-09 18:28:36 UTC (rev 14074)
@@ -0,0 +1,329 @@
+<?xml version="1.0" encoding="iso-8859-1"?>
+<chapter id="batch">
+    <title>Traitement par paquet</title>
+
+    <para>
+        Une approche naïve pour insérer 100 000 lignes dans la base de données en utilisant
+        Hibernate pourrait ressembler à ça :
+    </para>
+
+    <programlisting><![CDATA[Session session = sessionFactory.openSession();
+Transaction tx = session.beginTransaction();
+for ( int i=0; i<100000; i++ ) {
+    Customer customer = new Customer(.....);
+    session.save(customer);
+}
+tx.commit();
+session.close();]]></programlisting>
+
+    <para>
+        Ceci devrait s'écrouler avec une <literal>OutOfMemoryException</literal> quelque
+        part aux alentours de la 50 000ème ligne. C'est parce qu'Hibernate cache toutes
+        les instances de <literal>Customer</literal> nouvellement insérées dans le cache
+        de second niveau.
+    </para>
+
+    <para>
+        Dans ce chapitre nous montrerons comment éviter ce problème. D'abord, cependant,
+        si vous faites des traitements par batch, il est absolument critique que vous
+        activiez l'utilisation ds paquet JDBC (NdT : JDBC batching), si vous avez l'intention
+        d'obtenir des performances raisonnables. Configurez la taille du paquet JDBC avec un
+        nombre raisonnable (disons, 10-50) :
+    </para>
+
+    <programlisting><![CDATA[hibernate.jdbc.batch_size 20]]></programlisting>
+
+    <para>
+        Vous pourriez aussi vouloir faire cette sorte de travail dans un traitement où
+        l'interaction avec le cache de second niveau est complètement désactivé :
+    </para>
+
+    <programlisting><![CDATA[hibernate.cache.use_second_level_cache false]]></programlisting>
+
+    <sect1 id="batch-inserts">
+        <title>Insertions en paquet</title>
+
+        <para>
+            Lorsque vous rendez des nouveaux objets persistants, vous devez régulièrement appeler
+            <literal>flush()</literal> et puis <literal>clear()</literal> sur la session,
+            pour contrôler la taille du cache de premier niveau.
+        </para>
+
+        <programlisting><![CDATA[Session session = sessionFactory.openSession();
+Transaction tx = session.beginTransaction();
+
+for ( int i=0; i<100000; i++ ) {
+    Customer customer = new Customer(.....);
+    session.save(customer);
+    if ( i % 20 == 0 ) { //20, même taille que la taille du paquet JDBC
+        //flush un paquet d'insertions et libère la mémoire :
+        session.flush();
+        session.clear();
+    }
+}
+
+tx.commit();
+session.close();]]></programlisting>
+
+    </sect1>
+
+    <sect1 id="batch-update" >
+        <title>Paquet de mises à jour</title>
+
+        <para>
+            Pour récupérer et mettre à jour des données les mêmes idées s'appliquent. En plus,
+            vous avez besoin d'utiliser <literal>scroll()</literal> pour tirer partie des
+            curseurs côté serveur pour les requêtes qui retournent beaucoup de lignes de données.
+        </para>
+
+        <programlisting><![CDATA[Session session = sessionFactory.openSession();
+Transaction tx = session.beginTransaction();
+
+ScrollableResults customers = session.getNamedQuery("GetCustomers")
+    .setCacheMode(CacheMode.IGNORE)
+    .scroll(ScrollMode.FORWARD_ONLY);
+int count=0;
+while ( customers.next() ) {
+    Customer customer = (Customer) customers.get(0);
+    customer.updateStuff(...);
+    if ( ++count % 20 == 0 ) {
+        //flush un paquet de mises à jour et libère la mémoire :
+        session.flush();
+        session.clear();
+    }
+}
+
+tx.commit();
+session.close();]]></programlisting>
+
+    </sect1>
+
+    <sect1 id="batch-statelesssession">
+        <title>L'interface StatelessSession</title>
+        <para>
+            Alternativement, Hibernate fournit une API orientée commande qui peut être
+            utilisée avec des flux de données pour et en provenance de la base de données
+            sous la forme d'objets détachés. Une <literal>StatelessSession</literal> n'a pas
+            de contexte de persistance associé et ne fournit pas beaucoup de sémantique de
+            durée de vie de haut niveau. En particulier, une session sans état n'implémente
+            pas de cache de premier niveau et n'interagit pas non plus avec un cache de
+            seconde niveau ou un cache de requêtes. Elle n'implémente pas les transactions
+            ou la vérification sale automatique (NdT : automatic dirty checking). Les
+            opérations réalisées avec une session sans état ne sont jamais répercutées
+            en cascade sur les instances associées. Les collections sont ignorées par une
+            session sans état. Les opérations exécutées via une session sans état outrepasse
+            le modèle d'événements d'Hibernate et les intercepteurs. Les sessions sans état sont
+            vulnérables aux effets de modification des données, ceci est dû au manque de cache
+            de premier niveau. Une session sans état est une abstraction bas niveau, plus
+            proche de la couche JDBC sous-jacente.
+        </para>
+
+        <programlisting><![CDATA[StatelessSession session = sessionFactory.openStatelessSession();
+Transaction tx = session.beginTransaction();
+
+ScrollableResults customers = session.getNamedQuery("GetCustomers")
+    .scroll(ScrollMode.FORWARD_ONLY);
+while ( customers.next() ) {
+    Customer customer = (Customer) customers.get(0);
+    customer.updateStuff(...);
+    session.update(customer);
+}
+
+tx.commit();
+session.close();]]></programlisting>
+
+        <para>
+            Notez que dans le code de l'exemple, les intances de <literal>Customer</literal>
+            retournées par la requête sont immédiatement détachées. Elles ne sont jamais
+            associées à un contexte de persistance.
+        </para>
+
+        <para>
+            Les opérations <literal>insert()</literal>, <literal>update()</literal> et
+            <literal>delete()</literal> définies par l'interface <literal>StatelessSession</literal>
+            sont considérées comme des opérations d'accès direct aux lignes de la base de données,
+            ce qui résulte en une exécution immédiate du SQL <literal>INSERT</literal>, <literal>UPDATE</literal>
+            ou <literal>DELETE</literal> respectif. De là, elles ont des sémantiques tres différentes des
+            opérations <literal>save()</literal>, <literal>saveOrUpdate()</literal>
+            et <literal>delete()</literal> définies par l'interface <literal>Session</literal>.
+        </para>
+
+    </sect1>
+
+    <sect1 id="batch-direct" revision="2">
+        <title>Opérations de style DML</title>
+
+        <para>
+            Comme déjà discuté avant, le mapping objet/relationnel automatique et transparent
+            est intéressé par la gestion de l'état de l'objet. Ceci implique que l'état de l'objet
+            est disponible en mémoire, d'où manipuler (en utilisant des expressions du langage de
+            manipulation de données - <literal>Data Manipulation Language</literal> (DML) - SQL)
+            les données directement dans la base n'affectera pas l'état en mémoire. Pourtant, Hibernate
+            fournit des méthodes pour l'exécution d'expression DML de style SQL lesquelles sont
+            réalisées à travers le langage de requête d'Hibernate (<xref linkend="queryhql">HQL</xref>).
+        </para>
+
+        <para>
+            La pseudo-syntaxe pour les expressions <literal>UPDATE</literal> et <literal>DELETE</literal>
+            est : <literal>( UPDATE | DELETE ) FROM? EntityName (WHERE where_conditions)?</literal>.
+            Certains points sont à noter :
+        </para>
+
+        <itemizedlist spacing="compact">
+            <listitem>
+                <para>
+                    Dans la clause from, le mot-clef FROM est optionnel
+                </para>
+            </listitem>
+            <listitem>
+                <para>
+                    Il ne peut y avoir qu'une seule entité nommée dans la clause from ; elle peut
+                    optionnellement avoir un alias. Si le nom de l'entité a un alias, alors
+                    n'importe quelle référence de propriété doit être qualifiée en ayant un alias ;
+                    si le nom de l'entité n'a pas d'alias, alors il est illégal pour n'importe quelle
+                    référence de propriété d'être qualifiée.
+                </para>
+            </listitem>
+            <listitem>
+                <para>
+                    Aucune jointure (implicite ou explicite) ne peut être spécifiée dans une requête HQL.
+                    Les sous-requêtes peuvent être utilisées dans la clause where ; les sous-requêtes,
+                    elles-mêmes, peuvent contenir des jointures.
+                </para>
+            </listitem>
+            <listitem>
+                <para>
+                    La clause where est aussi optionnelle.
+                </para>
+            </listitem>
+        </itemizedlist>
+
+        <para>
+            Par exemple, pour exécuter un <literal>UPDATE</literal> HQL, utilisez la méthode
+            <literal>Query.executeUpdate()</literal> (la méthode est données pour ceux
+            qui sont familiers avec <literal>PreparedStatement.executeUpdate()</literal> de
+            JDBC) :
+        </para>
+
+        <programlisting><![CDATA[Session session = sessionFactory.openSession();
+Transaction tx = session.beginTransaction();
+
+String hqlUpdate = "update Customer c set c.name = :newName where c.name = :oldName";
+// ou String hqlUpdate = "update Customer set name = :newName where name = :oldName";
+int updatedEntities = s.createQuery( hqlUpdate )
+        .setString( "newName", newName )
+        .setString( "oldName", oldName )
+        .executeUpdate();
+tx.commit();
+session.close();]]></programlisting>
+
+        <para>
+            Pour exécuter un <literal>DELETE</literal> HQL, utilisez la même méthode
+            <literal>Query.executeUpdate()</literal> :
+        </para>
+
+        <programlisting><![CDATA[Session session = sessionFactory.openSession();
+Transaction tx = session.beginTransaction();
+
+String hqlDelete = "delete Customer c where c.name = :oldName";
+// or String hqlDelete = "delete Customer where name = :oldName";
+int deletedEntities = s.createQuery( hqlDelete )
+        .setString( "oldName", oldName )
+        .executeUpdate();
+tx.commit();
+session.close();]]></programlisting>
+
+        <para>
+            La valeur du <literal>int</literal> retourné par la méthode <literal>Query.executeUpdate()</literal>
+            indique le nombre d'entités affectées par l'opération. Considérez que cela peut ou pas
+            corréler le nombre de lignes affectés dans la base de données. Une opération HQL
+            pourrait entraîner l'exécution de multiples expressions SQL réelles, pour des classes
+            filles mappées par jointure (NdT: join-subclass), par exemple. Le nombre retourné
+            indique le nombre d'entités réelles affectées par l'expression. Retour à l'exemple de la
+            classe fille mappée par jointure, un effacement d'une des classes filles peut réellement
+            entraîner des suppressions pas seulement dans la table qui mappe la classe fille, mais
+            aussi dans la table "racine" et potentillement dans les tables des classes filles plus bas
+            dans la hiérarchie d'héritage.
+        </para>
+
+        <para>
+            La pseudo-syntaxe pour l'expression <literal>INSERT</literal> est :
+            <literal>INSERT INTO EntityName properties_list select_statement</literal>. Quelques
+            points sont à noter :
+        </para>
+
+        <itemizedlist spacing="compact">
+            <listitem>
+                <para>
+                    Seule la forme INSERT INTO ... SELECT ... est supportée ; pas la forme INSERT INTO ... VALUES ... .
+                </para>
+                <para>
+                    La properties_list est analogue à la <literal>spécification de la colonne</literal>
+
+                    The properties_list is analogous to the <literal>column speficiation</literal> dans
+                    l'expression SQL <literal>INSERT</literal>. Pour les entités impliquées dans
+                    un héritage mappé, seules les propriétés directement définies à ce niveau de classe
+                    donné peuvent être utilisées dans properties_list. Les propriétés de la classe mère
+                    ne sont pas permises ; et les propriétés des classes filles n'ont pas de sens. En
+                    d'autres mots, les expressions <literal>INSERT</literal> par nature non polymorphiques.
+                </para>
+            </listitem>
+            <listitem>
+                <para>
+                    select_statement peut être n'importe quelle requête de sélection HQl valide, avec
+                    l'avertissement que les types de retour doivent correspondre aux types attendus par
+                    l'insertion. Actuellement, c'est vérifié durant la compilation de la requête plutôt
+                    que la vérification soit reléguée à la base de données. Notez cependant que cela
+                    pourrait poser des problèmes entre les <literal>Type</literal>s d'Hibernate qui
+                    sont <emphasis>équivalents</emphasis> opposé à <emphasis>égaux</emphasis>. Cela
+                    pourrait poser des problèmes avec des disparités entre une propriété définie
+                    comme un <literal>org.hibernate.type.DateType</literal> et une propriété définie
+                    comme un <literal>org.hibernate.type.TimestampType</literal>, même si la base de données
+                    ne ferait pas de distinction ou ne serait pas capable de gérer la conversion.
+                </para>
+            </listitem>
+            <listitem>
+                <para>
+                    Pour la propriéte id, l'expression d'insertion vous donne deux options. Vous
+                    pouvez soit spécifier explicitement la propriété id dans properties_list
+                    (auquel cas sa valeur est extraite de l'expression de sélection correspondante),
+                    soit l'omettre de properties_list (auquel cas une valeur générée est utilisée).
+                    Cette dernière option est seulement disponible en utilisant le générateur d'identifiant
+                    qui opère dans la base de données ; tenter d'utiliser cette option avec n'importe quel
+                    type de générateur "en mémoire" causera une exception durant l'analyse. Notez
+                    que pour les buts de cette discussion, les générateurs "en base" sont considérés
+                    être <literal>org.hibernate.id.SequenceGenerator</literal> (et ses classes filles)
+                    et n'importe quelles implémentations de
+                    <literal>org.hibernate.id.PostInsertIdentifierGenerator</literal>.
+                    L'exception la plus notable ici est <literal>org.hibernate.id.TableHiLoGenerator</literal>,
+                    qu ne peut pas être utilisée parce qu'il ne propose pas un moyen de d'exposer ses valeurs
+                    par un select.
+                </para>
+            </listitem>
+            <listitem>
+                <para>
+                    Pour des propriétés mappées comme <literal>version</literal> ou <literal>timestamp</literal>,
+                    l'expression d'insertion vous donne deux options. Vous pouvez soit spécifier la propriété dans
+                    properties_list (auquel cas sa valeur est extraite des expressions select correspondantes),
+                    soit l'omettre de properties_list (auquel cas la <literal>valeur de graine</literal>
+                    (NdT : seed value) définie par le <literal>org.hibernate.type.VersionType</literal> est utilisée).
+                </para>
+            </listitem>
+        </itemizedlist>
+
+        <para>
+            Un exemple d'exécution d'une expression <literal>INSERT</literal> HQL :
+        </para>
+
+        <programlisting><![CDATA[Session session = sessionFactory.openSession();
+Transaction tx = session.beginTransaction();
+
+String hqlInsert = "insert into DelinquentAccount (id, name) select c.id, c.name from Customer c where ...";
+int createdEntities = s.createQuery( hqlInsert )
+        .executeUpdate();
+tx.commit();
+session.close();]]></programlisting>
+
+    </sect1>
+
+</chapter>

Copied: core/trunk/documentation/manual/fr-FR/src/main/docbook/content/best_practices.xml (from rev 14070, core/trunk/documentation/manual/fr-FR/src/main/docbook/modules/best_practices.xml)
===================================================================
--- core/trunk/documentation/manual/fr-FR/src/main/docbook/content/best_practices.xml	                        (rev 0)
+++ core/trunk/documentation/manual/fr-FR/src/main/docbook/content/best_practices.xml	2007-10-09 18:28:36 UTC (rev 14074)
@@ -0,0 +1,240 @@
+<?xml version="1.0" encoding="iso-8859-1"?>
+<chapter id="best-practices" revision="3">
+    <title>Meilleures pratiques</title>
+
+    <variablelist spacing="compact">
+        <varlistentry>
+            <term>Découpez finement vos classes et mappez les en utilisant <literal>&lt;component&gt;</literal>.</term>
+            <listitem>
+                <para>
+                    Utilisez une classe <literal>Adresse</literal> pour encapsuler <literal>Rue</literal>,
+                    <literal>Region</literal>, <literal>CodePostal</literal>.
+                    Ceci permet la réutilisation du code et simplifie la maintenance.
+                </para>
+            </listitem>
+        </varlistentry>
+        <varlistentry>
+            <term>Déclarez des propriétés d'identifiants dans les classes persistantes.</term>
+            <listitem>
+                <para>
+                    Hibernate rend les propriétés d'identifiants optionnelles. Il existe beaucoup de raisons
+                    pour lesquelles vous devriez les utiliser. Nous recommandons que vous utilisiez des identifiants
+		    techniques (générés, et sans connotation métier).
+                </para>
+            </listitem>
+        </varlistentry>
+        <varlistentry>
+            <term>Identifiez les clefs naturelles.</term>
+            <listitem>
+                <para>
+                    Identifiez les clefs naturelles pour toutes les entités, et mappez les avec
+                    <literal>&lt;natural-id&gt;</literal>. Implémentez <literal>equals()</literal> et
+                    <literal>hashCode()</literal> pour comparer les propriétés qui composent la clef naturelle.
+                </para>
+            </listitem>
+        </varlistentry>
+        <varlistentry>
+            <term>Placez chaque mapping de classe dans son propre fichier.</term>
+            <listitem>
+                <para>
+                    N'utilisez pas un unique document de mapping. Mappez <literal>com.eg.Foo</literal> dans
+                    le fichier <literal>com/eg/Foo.hbm.xml</literal>. Cela prend tout son sens lors
+                    d'un travail en équipe.
+                </para>
+            </listitem>
+        </varlistentry>
+        <varlistentry>
+            <term>Chargez les mappings comme des ressources.</term>
+            <listitem>
+                <para>
+                    Déployez les mappings en même temps que les classes qu'ils mappent.
+                </para>
+            </listitem>
+        </varlistentry>
+        <varlistentry>
+            <term>Pensez à externaliser les chaînes de caractères.</term>
+            <listitem>
+                <para>
+                    Ceci est une bonne habitude si vos requêtes appellent des fonctions SQL qui ne sont
+                    pas au standard ANSI. Cette externalisation dans les fichiers de mapping rendra votre
+		    application plus portable.
+                </para>
+            </listitem>
+        </varlistentry>
+        <varlistentry>
+            <term>Utilisez les variables "bindées".</term>
+            <listitem>
+                <para>
+                    Comme en JDBC, remplacez toujours les valeurs non constantes par "?". N'utilisez jamais
+                    la manipulation des chaînes de caractères pour remplacer des valeurs non constantes dans
+		     une requête ! Encore mieux, utilisez les paramètres nommés dans les requêtes.
+                </para>
+            </listitem>
+        </varlistentry>
+        <varlistentry>
+            <term>Ne gérez pas vous même les connexions JDBC.</term>
+            <listitem>
+                <para>
+                    Hibernate laisse l'application gérer les connexions JDBC. Vous ne devriez gérer vos connexions
+                    qu'en dernier recours. Si vous ne pouvez pas utiliser les systèmes de connexions livrés,
+		    réfléchissez à l'idée de fournir votre propre implémentation de <literal>org.hibernate.connection.ConnectionProvider</literal>.
+                </para>
+            </listitem>
+        </varlistentry>
+        <varlistentry>
+            <term>Pensez à utiliser les types utilisateurs.</term>
+            <listitem>
+                <para>
+                    Supposez que vous ayez une type Java, de telle bibliothèque, qui a besoin d'être persisté mais
+                    qui ne fournit pas les accesseurs nécessaires pour le mapper comme composant. Vous devriez
+		    implémenter
+                    <literal>org.hibernate.UserType</literal>.Cette approche libère le code de l'application
+                    de l'implémentation des transformations vers / depuis les types Hibernate.
+                </para>
+            </listitem>
+        </varlistentry>
+        <varlistentry>
+            <term>Utilisez du JDBC pur dans les goulets d'étranglement.</term>
+            <listitem>
+                <para>
+                    Dans certaines parties critiques de votre système d'un point de vue performance, quelques opérations
+                    peuvent tirer partie d'un appel JDBC natif.
+                    Mais attendez de <emphasis>savoir</emphasis>
+                    que c'est un goulet d'étranglement. Ne supposez jamais qu'un appel JDBC sera forcément plus
+                    rapide. Si vous avez besoin d'utiliser JDBC directement, ouvrez une <literal>Session</literal>
+                    Hibernate et utilisez la connexion SQL sous-jacente. Ainsi vous pourrez utiliser la même stratégie
+                    de transation et la même gestion des connexions.
+                </para>
+            </listitem>
+        </varlistentry>
+        <varlistentry>
+            <term>Comprendre le flush de <literal>Session</literal>.</term>
+            <listitem>
+                <para>
+                    De temps en temps la Session synchronise ses états persistants avec la base de données.
+                    Les performances seront affectées si ce processus arrive trop souvent. Vous pouvez parfois
+                    minimiser les flush non nécessaires en désactivant le flush automatique ou même en changeant
+                    l'ordre des opérations menées dans une transaction particulière.
+                </para>
+            </listitem>
+        </varlistentry>
+        <varlistentry>
+            <term>Dans une architecture à trois couches, pensez à utiliser <literal>saveOrUpdate()</literal>.</term>
+            <listitem>
+                <para>
+                    Quand vous utilisez une architecture à base de servlet / session bean, vous pourriez passer
+                    des objets chargés dans le bean session vers et depuis la couche servlet / JSP. Utilisez
+		    une nouvelle session pour traiter chaque requête.
+                    Utilisez <literal>Session.merge()</literal> ou <literal>Session.saveOrUpdate()</literal> pour
+                    synchroniser les objets avec la base de données.
+                </para>
+            </listitem>
+        </varlistentry>
+        <varlistentry>
+            <term>Dans une architecture à deux couches, pensez à utiliser la déconnexion de session.</term>
+            <listitem>
+                <para>
+                    Les transactions de bases de données doivent être aussi courtes que possible
+                    pour une meilleure montée en charge.Cependant, il est souvent nécessaire d'implémenter
+                    de longues <emphasis>transactions applicatives</emphasis>, une simple unité de travail du point de vue de
+                    l'utilisateur. Une transaction applicative
+                    peut s'étaler sur plusieurs cycles de requêtes/réponses du client.
+                    Il est commun d'utiliser des objets détachés pour implémenter des transactions applicatives.
+                    Une alternative, extrêmement appropriée dans une architecture à 2 couches, est de
+                    maintenir un seul contact de persistance ouvert (session) pour toute la durée de vie
+                    de la transaction applicative et simplement se déconnecter de la connexion JDBC à la fin de chaque requête,
+                    et se reconnecter au début de la requête suivante. Ne partagez jamais une seule
+                    session avec plus d'une transaction applicative, ou vous travaillerez avec des
+                    données périmées.
+                </para>
+            </listitem>
+        </varlistentry>
+        <varlistentry>
+            <term>Considérez que les exceptions ne sont pas rattrapables.</term>
+            <listitem>
+                <para>
+                    Il s'agit plus d'une pratique obligatoire que d'une "meilleure pratique". Quand une exception
+                    intervient, il faut faire un rollback de la <literal>Transaction</literal> et
+                    fermer la <literal>Session</literal>.
+                    Sinon, Hibernate ne peut garantir l'intégrité des états persistants en mémoire. En particulier,
+                    n'utilisez pas <literal>Session.load()</literal> pour déterminer si une instance avec un identifiant
+                    donné existe en base de données, utilisez <literal>Session.get()</literal> ou un requête.
+                </para>
+            </listitem>
+        </varlistentry>
+        <varlistentry>
+            <term>Préférez le chargement tardif des associations.</term>
+            <listitem>
+                <para>
+                    Utilisez le chargement complet avec modération.
+                    Utilisez les proxies et les collections chargées tardivement
+                    pour la plupart des associations vers des classes qui ne sont pas susceptibles
+                    d'être complètement retenues dans le cache de second niveau.
+                    Pour les assocations de classes en cache, où il y a une extrêmement
+                    forte probabilité que l'élément soit en cache, désactivez explicitement le chargement
+                    par jointures ouvertes en utilisant <literal>outer-join="false"</literal>.
+                    Lorsqu'un chargement par jointure ouverte est approprié pour un cas d'utilisation
+                    particulier, utilisez une requête avec un <literal>left join fetch</literal>.
+                </para>
+            </listitem>
+        </varlistentry>
+        <varlistentry>
+            <term>
+                Utilisez le pattern <emphasis>d'une ouverture de session dans une vue</emphasis>,
+                ou une <emphasis>phase d'assemblage</emphasis> disciplinée pour éviter des problèmes
+                avec des données non rapatriées.
+            </term>
+            <listitem>
+                <para>
+                    Hibernate libère les développeurs de l'écriture fastidieuse des <emphasis>objets de transfert
+                    de données (NdT : Data Transfer Objects)</emphasis> (DTO). Dans une architecture EJB traditionnelle,
+                    les DTOs ont deux buts : premièrement, ils contournent le problème des "entity bean" qui ne sont pas
+                    sérialisables ; deuxièmement, ils définissent implicitement une phase d'assemblage où toutes les
+                    données utilisées par la vue sont rapatriées et organisées dans les DTOs avant de retourner sous le
+                    contrôle de la couche de présentation. Hibernate élimine le premier but. Pourtant, vous aurez encore
+                    besoin d'une phase d'assemblage (pensez vos méthodes métier comme ayant un contrat strict avec la
+                    couche de présentation à propos de quelles données sont disponibles dans les objets détachés)
+                    à moins que vous soyez préparés à garder le contexte de
+                    persistance (la session) ouvert à travers tout le processus de rendu de la vue.
+                </para>
+            </listitem>
+        </varlistentry>
+        <varlistentry>
+            <term>Pensez à abstraite votre logique métier d'Hibernate.</term>
+            <listitem>
+                <para>
+                    Cachez le mécanisme d'accès aux données (Hibernate) derrière une interface. Combinez les patterns
+                    <emphasis>DAO</emphasis> et <emphasis>Thread Local Session</emphasis>. Vous pouvez même avoir quelques
+                    classes persistées par du JDBC pur, associées à Hibernate via un <literal>UserType</literal> (ce conseil est
+                    valable pour des applications de taille respectables ; il n'est pas valable pour une application
+                    avec cinq tables).
+                </para>
+            </listitem>
+        </varlistentry>
+        <varlistentry>
+            <term>N'utilisez pas d'associations de mapping exotiques.</term>
+            <listitem>
+                <para>
+                    De bons cas d'utilisation pour de vraies associations plusieurs-vers-plusieurs
+                    sont rares. La plupart du temps vous avez besoin d'informations additionnelles
+                    stockées dans la table d'association.
+                    Dans ce cas, il est préférable d'utiliser deux associations un-vers-plusieurs vers une classe
+                    de liaisons intermédiaire. En fait, nous pensons que la plupart des associations sont
+                    de type un-vers-plusieurs ou plusieurs-vers-un, vous devez être très attentifs lorsque
+                    vous utilisez autre chose et vous demander si c'est vraiment nécessaire.
+                </para>
+            </listitem>
+        </varlistentry>
+        <varlistentry>
+            <term>Préférez les associations bidirectionnelles.</term>
+            <listitem>
+                <para>
+                    Les associations unidirectionnelles sont plus difficiles à questionner.
+                    Dans une grande application, la plupart des associations devraient être navigables dans les deux directions dans les requêtes.
+                </para>
+            </listitem>
+        </varlistentry>
+    </variablelist>
+
+</chapter>
+

Copied: core/trunk/documentation/manual/fr-FR/src/main/docbook/content/collection_mapping.xml (from rev 14070, core/trunk/documentation/manual/fr-FR/src/main/docbook/modules/collection_mapping.xml)
===================================================================
--- core/trunk/documentation/manual/fr-FR/src/main/docbook/content/collection_mapping.xml	                        (rev 0)
+++ core/trunk/documentation/manual/fr-FR/src/main/docbook/content/collection_mapping.xml	2007-10-09 18:28:36 UTC (rev 14074)
@@ -0,0 +1,1216 @@
+<?xml version="1.0" encoding="iso-8859-1"?>
+<chapter id="collections">
+    <title>Mapping des collections</title>
+
+    <sect1 id="collections-persistent" revision="3">
+        <title>Collections persistantes</title>
+
+        <para>
+            Hibernate requiert que les champs contenant des collections persistantes soient déclarés
+            comme des types d'interface, par exemple :
+        </para>
+
+        <programlisting><![CDATA[public class Product {
+    private String serialNumber;
+    private Set parts = new HashSet();
+
+    public Set getParts() { return parts; }
+    void setParts(Set parts) { this.parts = parts; }
+    public String getSerialNumber() { return serialNumber; }
+    void setSerialNumber(String sn) { serialNumber = sn; }
+}]]></programlisting>
+
+        <para>
+            L'interface réelle devrait être <literal>java.util.Set</literal>,
+            <literal>java.util.Collection</literal>, <literal>java.util.List</literal>,
+            <literal>java.util.Map</literal>, <literal>java.util.SortedSet</literal>,
+            <literal>java.util.SortedMap</literal> ou ... n'importe quoi d'autre ! (Où
+            "n'importe quoi d'autre" signifie que vous devrez écrire une implémentation de
+            <literal>org.hibernate.usertype.UserCollectionType</literal>.)
+        </para>
+
+        <para>
+            Notez comment nous avons initialisé les variables d'instance avec une instance de
+            <literal>HashSet</literal>. C'est le meilleur moyen pour initialiser les 
+            collections d'instances nouvellement créées (non persistantes). Quand
+            nous fabriquons l'instance persistante - en appelant <literal>persist()</literal>,
+            par exemple - Hibernate remplacera réellement le <literal>HashSet</literal>
+            avec une instance d'une implémentation propre à Hibernate de <literal>Set</literal>.
+            Prenez garde aux erreurs :
+        </para>
+
+        <programlisting><![CDATA[Cat cat = new DomesticCat();
+Cat kitten = new DomesticCat();
+....
+Set kittens = new HashSet();
+kittens.add(kitten);
+cat.setKittens(kittens);
+session.persist(cat);
+kittens = cat.getKittens(); // Ok, la collection kittens est un Set
+(HashSet) cat.getKittens(); // Erreur !]]></programlisting>
+
+        <para>
+            Les collections persistantes injectées par Hibernate se comportent de la même manière que
+            <literal>HashMap</literal>, <literal>HashSet</literal>,
+            <literal>TreeMap</literal>, <literal>TreeSet</literal> ou
+            <literal>ArrayList</literal>, selon le type de l'interface.
+        </para>
+
+        <para>
+            Les instances des collections ont le comportement habituel des types des valeurs.
+            Elles sont automatiquement persistées quand elles sont référencées par un objet persistant et
+            automatiquement effacées quand elles sont déréférencées. Si une collection est passée
+            d'un objet persistant à un autre, ses éléments pourraient être déplacés d'une table
+            à une autre. Deux entités ne peuvent pas partager une référence vers une même instance
+            d'une collection. Dû au modèle relationnel sous-jacent, les propriétés contenant des
+            collections ne supportent pas la sémantique de la valeur null ; Hibernate ne distingue pas
+            une référence vers une collection nulle d'une collection vide.
+        </para>
+
+        <para>
+            Vous ne devriez pas vous préoccuper trop de ça. Utilisez les collections persistantes de
+            la même manière que vous utilisez des collections Java ordinaires. Assurez-vous
+            de comprendre la sémantique des associations bidirectionnelles (traitée plus loin).
+        </para>
+
+    </sect1>
+
+    <sect1 id="collections-mapping" revision="4">
+        <title>Mapper une collection</title>
+
+        <para>
+            L'élément de mapping d'Hibernate utilisé pour mapper une collection dépend du type de
+            l'interface. Par exemple, un élément <literal>&lt;set&gt;</literal> est utilisé
+            pour mapper des propriétés de type <literal>Set</literal>.
+        </para>
+
+        <programlisting><![CDATA[<class name="Product">
+    <id name="serialNumber" column="productSerialNumber"/>
+    <set name="parts">
+        <key column="productSerialNumber" not-null="true"/>
+        <one-to-many class="Part"/>
+    </set>
+</class>]]></programlisting>
+
+        <para>
+            À part <literal>&lt;set&gt;</literal>, il y  aussi les éléments de mapping
+            <literal>&lt;list&gt;</literal>, <literal>&lt;map&gt;</literal>,
+            <literal>&lt;bag&gt;</literal>, <literal>&lt;array&gt;</literal> et
+            <literal>&lt;primitive-array&gt;</literal>.
+            L'élément <literal>&lt;map&gt;</literal> est représentatif :
+        </para>
+
+        <programlistingco>
+            <areaspec>
+                <area id="mappingcollection1" coords="2 65"/>
+                <area id="mappingcollection2" coords="3 65"/>
+                <area id="mappingcollection3" coords="4 65"/>
+                <area id="mappingcollection4" coords="5 65"/>
+                <area id="mappingcollection5" coords="6 65"/>
+                <area id="mappingcollection6" coords="7 65"/>
+                <area id="mappingcollection7" coords="8 65"/>
+                <area id="mappingcollection8" coords="9 65"/>
+                <area id="mappingcollection9" coords="10 65"/>
+                <area id="mappingcollection10" coords="11 65"/>
+                <area id="mappingcollection11" coords="12 65"/>
+                <area id="mappingcollection12" coords="13 65"/>
+                <area id="mappingcollection13" coords="14 65"/>
+                <area id="mappingcollection14" coords="15 65"/>
+            </areaspec>
+            <programlisting><![CDATA[<map
+    name="nomDePropriete"
+    table="nom_de_table"
+    schema="nom_du_schema"
+    lazy="true|extra|false"
+    inverse="true|false"
+    cascade="all|none|save-update|delete|all-delete-orphan"
+    sort="unsorted|natural|ClasseDeComparateur"
+    order-by="nom_de_column asc|desc"
+    where="condition sql where quelcconque"
+    fetch="join|select|subselect"
+    batch-size="N"
+    access="field|property|NomDeClasse"
+    optimistic-lock="true|false"
+    mutable="true|false"
+    node="nom-d-element|."
+    embed-xml="true|false"
+>
+
+    <key .... />
+    <map-key .... />
+    <element .... />
+</map>]]></programlisting>
+            <calloutlist>
+                <callout arearefs="mappingcollection1">
+                    <para>
+                        <literal>name</literal> : le nom de la propriété contenant la collection
+                    </para>
+                </callout>
+                <callout arearefs="mappingcollection2">
+                    <para>
+                        <literal>table</literal> (optionnel - par défaut = nom de la propriété) : le
+                        nom de la table de la collection (non utilisé pour les associations one-to-many)
+                    </para>
+                </callout>
+                <callout arearefs="mappingcollection3">
+                    <para>
+                        <literal>schema</literal> (optionnel) : le nom du schéma pour surcharger le
+                        schéma déclaré dans l'élément racine
+                    </para>
+                </callout>
+                <callout arearefs="mappingcollection4">
+                    <para>
+                        <literal>lazy</literal> (optionnel - par défaut = <literal>true</literal>) :
+                        peut être utilisé pour désactiver l'initialisation tardive et spécifier
+                        que l'association est toujours rapportée, ou pour activer la
+                        récupération extra-paresseuse (NdT : extra-lazy) où la plupart des
+                        opérations n'initialisent pas la collection (approprié pour de très
+                        grosses collections)
+                    </para>
+                </callout>
+                <callout arearefs="mappingcollection5">
+                    <para>
+                        <literal>inverse</literal> (optionnel - par défaut = <literal>false</literal>) :
+                        définit cette collection comme l'extrêmité "inverse" de l'association
+                        bidirectionnelle
+                    </para>
+                </callout>
+                <callout arearefs="mappingcollection6">
+                    <para>
+                        <literal>cascade</literal> (optionnel - par défaut = <literal>none</literal>) :
+                        active les opérations de cascade vers les entités filles
+                    </para>
+                </callout>
+                <callout arearefs="mappingcollection7">
+                    <para>
+                        <literal>sort</literal> (optionnel) : spécifie une collection triée via un ordre
+                        de tri <literal>naturel</literal>, ou via une classe comparateur donnée (implémentant Comparator)
+                    </para>
+                </callout>
+                <callout arearefs="mappingcollection8">
+                    <para>
+                        <literal>order-by</literal> (optionnel, seulement à partir du JDK1.4) :
+                        spécifie une colonne de table
+                        (ou des colonnes) qui définit l'ordre d'itération de <literal>Map</literal>, <literal>Set</literal>
+                        ou Bag, avec en option <literal>asc</literal> ou <literal>desc</literal>
+                    </para>
+                </callout>
+                <callout arearefs="mappingcollection9">
+                    <para>
+                        <literal>where</literal> (optionnel) : spécifie une condition SQL arbitraire <literal>WHERE</literal>
+                        à utiliser au chargement ou à la suppression d'une collection (utile si la collection
+                        ne doit contenir qu'un sous ensemble des données disponibles)
+                    </para>
+                </callout>
+                <callout arearefs="mappingcollection10">
+                    <para>
+                        <literal>fetch</literal> (optionnel, par défaut = <literal>select</literal>) :
+                        à choisir entre récupération par jointures externes, récupération par
+                        selects séquentiels, et récupération par sous-selects séquentiels
+                    </para>
+                </callout>
+                <callout arearefs="mappingcollection11">
+                    <para>
+                        <literal>batch-size</literal> (optionnel, par défaut = <literal>1</literal>) : une taille
+                        de batch (batch size) utilisée pour charger plusieurs instances de cette collection en
+                        initialisation tardive
+                    </para>
+                </callout>
+                <callout arearefs="mappingcollection12">
+                    <para>
+                        <literal>access</literal> (optionnel - par défaut = <literal>property</literal>) : La
+                        stratégie qu'Hibernate doit utiliser pour accéder à la valeur de la propriété
+                    </para>
+                </callout>
+                <callout arearefs="mappingcollection13">
+                    <para>
+                        <literal>optimistic-lock</literal> (optionnel - par défaut = <literal>true</literal>) :
+                        spécifie que changer l'état de la collection entraîne l'incrémentation
+                        de la version appartenant à l'entité (Pour une association un vers plusieurs,
+                        il est souvent raisonnable de désactiver ce paramètre)
+                    </para>
+                </callout>
+                <callout arearefs="mappingcollection14">
+                    <para>
+                        <literal>mutable</literal> (optionnel - par défaut = <literal>true</literal>) :
+                        une valeur à <literal>false</literal> spécifie que les éléments de la
+                        collection ne changent jamais (une optimisation mineure dans certains cas)
+                    </para>
+                </callout>
+            </calloutlist>
+        </programlistingco>
+
+        <sect2 id="collections-foreignkeys" >
+           <title>Les clefs étrangères d'une collection</title>
+
+            <para>
+                Les instances d'une collection sont distinguées dans la base par la clef étrangère
+                de l'entité qui possède la collection. Cette clef étrangère est référencée comme la(es)
+                <emphasis>colonne(s) de la clef de la collection</emphasis> de la table de la collection.
+                La colonne de la clef de la collection est mappée par l'élément <literal>&lt;key&gt;</literal>.
+            </para>
+
+            <para>
+                Il peut y avoir une contrainte de nullité sur la colonne de la clef étrangère. Pour les
+                associations unidirectionnelles un vers plusieurs, la colonne de la clef étrangère
+                peut être nulle par défaut, donc vous pourriez avoir besoin de spécifier
+                <literal>not-null="true"</literal>.
+            </para>
+
+            <programlisting><![CDATA[<key column="productSerialNumber" not-null="true"/>]]></programlisting>
+
+            <para>
+                La contraite de la clef étrangère peut utiliser <literal>ON DELETE CASCADE</literal>.
+            </para>
+
+            <programlisting><![CDATA[<key column="productSerialNumber" on-delete="cascade"/>]]></programlisting>
+
+            <para>
+                Voir le chapitre précédent pour une définition complète de l'élément <literal>&lt;key&gt;</literal>.
+            </para>
+
+        </sect2>
+
+        <sect2 id="collections-elements" >
+            <title>Les éléments d'une collection</title>
+
+            <para>
+                Les collections peuvent contenir la plupart des autres types Hibernate, dont tous les types
+                basiques, les types utilisateur, les composants, et bien sûr, les références vers
+                d'autres entités. C'est une distinction importante : un objet dans une collection
+                pourrait être géré avec une sémantique de "valeur" (sa durée de vie dépend complètement
+                du propriétaire de la collection) ou il pourrait avoir une référence vers une autre
+                entité, avec sa propre durée de vie. Dans le dernier cas, seul le "lien" entre les 2 objets
+                est considéré être l'état retenu par la collection.
+            </para>
+
+            <para>
+                Le type contenu est référencé comme le <emphasis>type de l'élément de la collection</emphasis>.
+                Les éléments de la collections sont mappés par <literal>&lt;element&gt;</literal> ou
+                <literal>&lt;composite-element&gt;</literal>, ou dans le cas des références d'entité, avec
+                <literal>&lt;one-to-many&gt;</literal> ou <literal>&lt;many-to-many&gt;</literal>.
+                Les deux premiers mappent des éléments avec un sémantique de valeur, les deux suivants sont
+                utilisés pour mapper des associations d'entité.
+            </para>
+
+        </sect2>
+
+        <sect2 id="collections-indexed">
+            <title>Collections indexées</title>
+
+            <para>
+                Tous les mappings de collection, exceptés ceux avec les sémantiques d'ensemble (NdT : set) et
+                de sac (NdT : bag), ont besoin d'une <emphasis>colonne d'index</emphasis> dans la
+                table de la collection - une colonne qui mappe un index de tableau, ou un index de
+                <literal>List</literal>, ou une clef de <literal>Map</literal>. L'index d'une
+                <literal>Map</literal> peut être n'importe quel type basique, mappé avec
+                <literal>&lt;map-key&gt;</literal>, ça peut être une référence d'entité mappée avec
+                <literal>&lt;map-key-many-to-many&gt;</literal>, ou ça peut être un type composé, mappé avec
+                <literal>&lt;composite-map-key&gt;</literal>. L'index d'un tableau ou d'une liste est toujours
+                de type <literal>integer</literal> et est mappé en utilisant l'élément <literal>&lt;list-index&gt;</literal>.
+                Les colonnes mappées contiennent des entiers séquentiels (numérotés à partir de zéro par défaut).
+            </para>
+
+        <programlistingco>
+            <areaspec>
+                <area id="index1" coords="2 45"/>
+                <area id="index2" coords="3 45"/>
+             </areaspec>
+            <programlisting><![CDATA[<list-index
+        column="nom_de_colonne"
+        base="0|1|..."/>]]></programlisting>
+            <calloutlist>
+                <callout arearefs="index1">
+                    <para>
+                        <literal>nom_de_colonne</literal> (requis) : le nom de la colonne contenant les valeurs de l'index de la collection
+                    </para>
+                </callout>
+                <callout arearefs="index1">
+                    <para>
+                        <literal>base</literal> (optionnel, par défaut = <literal>0</literal>) : la valeur
+                        de la colonne de l'index qui correspond au premier élément de la liste ou du tableau
+                    </para>
+                </callout>
+            </calloutlist>
+        </programlistingco>
+
+        <programlistingco>
+            <areaspec>
+                <area id="mapkey1" coords="2 45"/>
+                <area id="mapkey2" coords="3 45"/>
+                <area id="mapkey3" coords="4 45"/>
+             </areaspec>
+            <programlisting><![CDATA[<map-key
+        column="nom_de_colonne"
+        formula="n'importe quelle expression SQL"
+        type="nom_du_type"
+        node="@nom-d-attribut"
+        length="N"/>]]></programlisting>
+            <calloutlist>
+                <callout arearefs="mapkey1">
+                    <para>
+                        <literal>column</literal> (optionnel) :
+                        le nom de la colonne contenant les valeurs de l'index de la collection
+                    </para>
+                </callout>
+                <callout arearefs="mapkey2">
+                    <para>
+                        <literal>formula</literal> (optionnel) :
+                        une formule SQL utilisée pour évaluer la clef de la map
+                    </para>
+                </callout>
+                <callout arearefs="mapkey3">
+                    <para>
+                        <literal>type</literal> (reguis): le type des clefs de la map
+                    </para>
+                </callout>
+            </calloutlist>
+        </programlistingco>
+
+        <programlistingco>
+            <areaspec>
+                <area id="indexmanytomany1" coords="2 45"/>
+                <area id="indexmanytomany2" coords="3 45"/>
+                <area id="indexmanytomany3" coords="3 45"/>
+             </areaspec>
+            <programlisting><![CDATA[<map-key-many-to-many
+        column="nom_de_colonne"
+        formula="n'importe quelle expression SQL"
+        class="NomDeClasse"
+/>]]></programlisting>
+            <calloutlist>
+                <callout arearefs="indexmanytomany1">
+                    <para>
+                        <literal>column</literal> (optionnel) :
+                        le nom de la colonne de la clef étrangère pour les valeurs de l'index de la collection
+                    </para>
+                </callout>
+                <callout arearefs="indexmanytomany2">
+                    <para>
+                        <literal>formula</literal> (optionnel) :
+                        une formulre SQL utilisée pour évaluer la clef étrangère de la clef de la map
+                    </para>
+                </callout>
+                <callout arearefs="indexmanytomany3">
+                    <para>
+                        <literal>class</literal> (requis): la classe de l'entité utilisée comme clef de la map
+                    </para>
+                </callout>
+            </calloutlist>
+        </programlistingco>
+            <para>
+                Si votre table n'a pas de colonne d'index, et que vous souhaitez tout de même utiliser
+                <literal>List</literal> comme type de propriété, vous devriez mapper la propriété comme un
+                <emphasis>&lt;bag&gt;</emphasis> Hibernate. Un sac (NdT : bag) ne garde pas son ordre quand
+                il est récupéré de la base de données, mais il peut être optionnellement trié ou ordonné.
+            </para>
+
+        </sect2>
+
+        <para>
+            Il y a pas mal de variétés de mappings qui peuvent être générés pour les collections,
+            couvrant beaucoup des modèles relationnels communs. Nous vous suggérons d'expérimenter avec l'outil de
+            génération de schéma pour avoir une idée de comment traduire les différentes déclarations de mapping vers des table de la base de données.
+        </para>
+
+    <sect2 id="collections-ofvalues" revision="2">
+        <title>Collections de valeurs et associations plusieurs-vers-plusieurs</title>
+
+        <para>
+            N'importe quelle collection de valeurs ou association plusieurs-vers-plusieurs requiert une
+            <emphasis>table de collection</emphasis> avec une(des) colonne(s) de clef étrangère, une(des)
+            <emphasis>colonne(s) d'élément de la collection</emphasis> ou des colonnes et possiblement
+            une(des) colonne(s) d'index.
+        </para>
+
+        <para>
+            Pour une collection de valeurs, nous utilisons la balise <literal>&lt;element&gt;</literal>.
+        </para>
+
+        <programlistingco>
+            <areaspec>
+                <area id="element1b" coords="2 50"/>
+                <area id="element2b" coords="3 50"/>
+                <area id="element3b" coords="4 50"/>
+             </areaspec>
+            <programlisting><![CDATA[<element
+        column="nom_de_colonne"
+        formula="n'importe quelle expression SQL"
+        type="nomDeType"
+        length="L"
+        precision="P"
+        scale="S"
+        not-null="true|false"
+        unique="true|false"
+        node="nom-d-element"
+/>]]></programlisting>
+            <calloutlist>
+                <callout arearefs="element1b">
+                    <para>
+                        <literal>column</literal> (optionnel) : le nom de la colonne contenant les valeurs de l'élément de la collection
+                    </para>
+                </callout>
+                <callout arearefs="element2b">
+                    <para>
+                        <literal>formula</literal> (optionnel) : une formule SQL utilisée pour évaluer l'élément
+                    </para>
+                </callout>
+                <callout arearefs="element3b">
+                    <para>
+                        <literal>type</literal> (requis) : le type de l'élément de la collection
+                    </para>
+                </callout>
+            </calloutlist>
+        </programlistingco>
+
+        <para>
+            Une <emphasis>association plusieurs-vers-plusieurs</emphasis> est spécifiée en
+            utilisant l'élément <literal>&lt;many-to-many&gt;</literal>.
+        </para>
+
+        <programlistingco>
+            <areaspec>
+                <area id="manytomany1" coords="2 60"/>
+                <area id="manytomany2" coords="3 60"/>
+                <area id="manytomany3" coords="4 60"/>
+                <area id="manytomany4" coords="5 60"/>
+                <area id="manytomany5" coords="6 60"/>
+                <area id="manytomany6" coords="7 60"/>
+                <area id="manytomany7" coords="8 60"/>
+                <area id="manytomany8" coords="9 60"/>
+            </areaspec>
+            <programlisting><![CDATA[<many-to-many
+        column="nom_de_colonne"
+        formula="n'importe quelle expression SQL"
+        class="NomDeClasse"
+        fetch="select|join"
+        unique="true|false"
+        not-found="ignore|exception"
+        entity-name="NomDEntite"
+        property-ref="nomDeProprieteDeLaClasseAssociee"
+        node="nom-d-element"
+        embed-xml="true|false"
+    />]]></programlisting>
+            <calloutlist>
+                <callout arearefs="manytomany1">
+                    <para>
+                        <literal>column</literal> (optionnel) : le nom de la colonne de la clef étrangère de l'élément
+                    </para>
+                </callout>
+                <callout arearefs="manytomany2">
+                    <para>
+                        <literal>formula</literal> (optionnel) :
+                        une formule SQL utilisée pour évaluer la valeur de la clef étrangère de l'élément
+                    </para>
+                </callout>
+                <callout arearefs="manytomany3">
+                    <para>
+                        <literal>class</literal> (requis) : le nom de la classe associée
+                    </para>
+                </callout>
+                <callout arearefs="manytomany4">
+                    <para>
+                        <literal>fetch</literal> (optionnel - par défaut <literal>join</literal>) :
+                        active les récupérations par jointures externes ou par selects séquentiels pour cette association.
+                        C'est un cas spécial ; pour une récupération complète sans attente (dans un seul <literal>SELECT</literal>) d'une
+                        entité et de ses relations plusieurs-vers-plusieurs vers d'autres entités,
+                        vous devriez activer la récupération <literal>join</literal> non seulement sur
+                        la collection elle-même, mais aussi avec cet attribut sur l'élément imbriqué
+                        <literal>&lt;many-to-many&gt;</literal>.
+                    </para>
+                </callout>
+                <callout arearefs="manytomany5">
+                    <para>
+                        <literal>unique</literal> (optionnel) : activer la génération DDL d'une
+                        contrainte d'unicité pour la colonne de la clef étrangère. Ça rend la pluralité
+                        de l'association effectivement un-vers-plusieurs.
+                    </para>
+                </callout>
+	            <callout arearefs="manytomany6">
+	                <para>
+	                    <literal>not-found</literal> (optionnel - par défaut <literal>exception</literal>) :
+                            spécifie comment les clefs étrangères qui référencent la lignes
+                            manquantes seront gérées : <literal>ignore</literal> traitera
+                            une ligne manquante comme une association nulle.
+	                </para>
+	            </callout>
+                <callout arearefs="manytomany7">
+                    <para>
+                        <literal>entity-name</literal> (optionnel) : le nom de l'entité de la classe associée, comme une alternative à <literal>class</literal>
+                    </para>
+                </callout>
+                <callout arearefs="manytomany8">
+                    <para>
+                        <literal>property-ref</literal> (optionnel) : le nom d'une propriété de
+                        la classe associée qui est jointe à cette clef étrangère. Si non spécifiée,
+                        la clef primaire de la classe associée est utilisée.
+                    </para>
+                </callout>
+            </calloutlist>
+        </programlistingco>
+
+        <para>
+            Quelques exemples, d'abord, un ensemble de chaînes de caractères :
+        </para>
+
+        <programlisting><![CDATA[<set name="names" table="person_names">
+    <key column="person_id"/>
+    <element column="person_name" type="string"/>
+</set>]]></programlisting>
+
+        <para>
+            Un bag contenant des entiers (avec un ordre d'itération déterminé par l'attribut <literal>order-by</literal>) :
+        </para>
+
+        <programlisting><![CDATA[<bag name="sizes"
+        table="item_sizes"
+        order-by="size asc">
+    <key column="item_id"/>
+    <element column="size" type="integer"/>
+</bag>]]></programlisting>
+
+        <para>
+            Un tableau d'entités - dans ce cas, une association plusieurs-vers-plusieurs :
+        </para>
+
+        <programlisting><![CDATA[<array name="addresses"
+        table="PersonAddress"
+        cascade="persist">
+    <key column="personId"/>
+    <list-index column="sortOrder"/>
+    <many-to-many column="addressId" class="Address"/>
+</array>]]></programlisting>
+
+        <para>
+            Une map de chaînes de caractères vers des dates :
+        </para>
+
+        <programlisting><![CDATA[<map name="holidays"
+        table="holidays"
+        schema="dbo"
+        order-by="hol_name asc">
+    <key column="id"/>
+    <map-key column="hol_name" type="string"/>
+    <element column="hol_date" type="date"/>
+</map>]]></programlisting>
+
+        <para>
+            Une liste de composants (discute dans le prochain chapitre) :
+        </para>
+
+        <programlisting><![CDATA[<list name="carComponents"
+        table="CarComponents">
+    <key column="carId"/>
+    <list-index column="sortOrder"/>
+    <composite-element class="CarComponent">
+        <property name="price"/>
+        <property name="type"/>
+        <property name="serialNumber" column="serialNum"/>
+    </composite-element>
+</list>]]></programlisting>
+
+    </sect2>
+
+    <sect2 id="collections-onetomany">
+        <title>Association un-vers-plusieurs</title>
+
+        <para>
+            Une <emphasis>association un vers plusieurs</emphasis> lie les tables de deux classes
+            par une clef étrangère, sans l'intervention d'une table de collection. Ce mapping perd certaines sémantiques des collections Java normales :
+        </para>
+
+        <itemizedlist spacing="compact">
+            <listitem>
+                <para>
+                    Une instance de la classe de l'entité contenue ne peut pas appartenir à plus d'une
+                    instance de la collection
+                </para>
+            </listitem>
+            <listitem>
+                <para>
+                    Une instance de la classe de l'entité contenue ne peut pas apparaître plus plus d'une valeur d'index de la collection
+                </para>
+            </listitem>
+        </itemizedlist>
+
+        <para>
+            Une association de <literal>Product</literal> vers <literal>Part</literal> requiert l'existence d'une
+            clef étrangère et possiblement une colonne d'index pour la table <literal>Part</literal>. Une balise
+            <literal>&lt;one-to-many&gt;</literal> indique que c'est une association un vers plusieurs.
+        </para>
+
+        <programlistingco>
+            <areaspec>
+                <area id="onetomany1" coords="2 60"/>
+                <area id="onetomany2" coords="3 60"/>
+                <area id="onetomany3" coords="4 60"/>
+            </areaspec>
+            <programlisting><![CDATA[<one-to-many
+        class="NomDeClasse"
+        not-found="ignore|exception"
+        entity-name="NomDEntite"
+        node="nom-d-element"
+        embed-xml="true|false"
+    />]]></programlisting>
+            <calloutlist>
+                <callout arearefs="onetomany1">
+                    <para>
+                        <literal>class</literal> (requis) : le nom de la classe associée
+                    </para>
+                </callout>
+                <callout arearefs="onetomany2">
+                    <para>
+                        <literal>not-found</literal> (optionnel - par défaut <literal>exception</literal>) :
+                        spécifie comment les identifiants cachés qui référencent des lignes manquantes seront gérés :
+                        <literal>ignore</literal> traitera une ligne manquante comme une association nulle
+                    </para>
+                </callout>
+                <callout arearefs="onetomany3">
+                    <para>
+                        <literal>entity-name</literal> (optionnel) : le nom de l'entité de la
+                        classe associée, comme une alternative à <literal>class</literal>.
+                    </para>
+                </callout>
+            </calloutlist>
+       </programlistingco>
+
+        <para>
+            Notez que l'élément <literal>&lt;one-to-many&gt;</literal> n'a pas besoin de déclarer de colonnes. Il n'est pas non plus nécessaire de spécifier le nom de la table nulle part.
+        </para>
+
+        <para>
+            <emphasis>Note très importante :</emphasis> si la colonne de la clef d'une association
+            <literal>&lt;one-to-many&gt;</literal> est déclarée <literal>NOT NULL</literal>, vous devez déclarer le
+            mapping de <literal>&lt;key&gt;</literal> avec <literal>not-null="true"</literal> ou
+            <emphasis>utiliser une association bidirectionnelle</emphasis> avec le mapping de la
+            collection marqué <literal>inverse="true"</literal>. Voir la discussion sur les associations bidirectionnelles plus tard dans ce chapitre.
+        </para>
+
+        <para>
+            Cet exemple montre une map d'entités <literal>Part</literal> par nom (où
+            <literal>partName</literal> est une propriété persistante de <literal>Part</literal>).
+            Notez l'utilisation d'un index basé sur une formule.
+        </para>
+
+        <programlisting><![CDATA[<map name="parts"
+        cascade="all">
+    <key column="productId" not-null="true"/>
+    <map-key formula="partName"/>
+    <one-to-many class="Part"/>
+</map>]]></programlisting>
+    </sect2>
+
+    </sect1>
+
+    <sect1 id="collections-advancedmappings">
+        <title>Mappings de collection avancés</title>
+
+    <sect2 id="collections-sorted" revision="2">
+        <title>Collections triées</title>
+
+        <para>
+            Hibernate supporte des collections implémentant <literal>java.util.SortedMap</literal> et
+            <literal>java.util.SortedSet</literal>. Vous devez spécifier un comparateur dans le fichier de mapping :
+        </para>
+
+        <programlisting><![CDATA[<set name="aliases"
+            table="person_aliases"
+            sort="natural">
+    <key column="person"/>
+    <element column="name" type="string"/>
+</set>
+
+<map name="holidays" sort="my.custom.HolidayComparator">
+    <key column="year_id"/>
+    <map-key column="hol_name" type="string"/>
+    <element column="hol_date" type="date"/>
+</map>]]></programlisting>
+
+        <para>
+            Les valeurs permises pour l'attribut <literal>sort</literal> sont <literal>unsorted</literal>,
+            <literal>natural</literal> et le nom d'une classe implémentant
+            <literal>java.util.Comparator</literal>.
+        </para>
+
+        <para>
+            Les collections triées se comportent réellement comme <literal>java.util.TreeSet</literal> ou
+            <literal>java.util.TreeMap</literal>.
+        </para>
+
+        <para>
+            Si vous voulez que la base de données elle-même ordonne les éléments de la collection, utilisez l'attribut
+            <literal>order-by</literal> des mappings <literal>set</literal>, <literal>bag</literal>
+            ou <literal>map</literal>. Cette solution est seulement disponible à partir du JDK 1.4 (c'est
+            implémenté en utilisant <literal>LinkedHashSet</literal> ou
+            <literal>LinkedHashMap</literal>). Ceci exécute le tri dans la requête SQL, pas en mémoire.
+        </para>
+
+        <programlisting><![CDATA[<set name="aliases" table="person_aliases" order-by="lower(name) asc">
+    <key column="person"/>
+    <element column="name" type="string"/>
+</set>
+
+<map name="holidays" order-by="hol_date, hol_name">
+    <key column="year_id"/>
+    <map-key column="hol_name" type="string"/>
+    <element column="hol_date type="date"/>
+</map>]]></programlisting>
+
+        <para>
+            Notez que la valeur de l'attribut <literal>order-by</literal> est un ordre SQL, pas un ordre HQL !
+        </para>
+
+        <para>
+            Les associations peuvent même être triées sur des critères arbitraires à l'exécution en utilisant un <literal>filter()</literal> de collection.
+        </para>
+
+        <programlisting><![CDATA[sortedUsers = s.createFilter( group.getUsers(), "order by this.name" ).list();]]></programlisting>
+
+    </sect2>
+
+     <sect2 id="collections-bidirectional" revision="1">
+        <title>Associations bidirectionnelles</title>
+
+        <para>
+            Une <emphasis>association bidirectionnelle</emphasis> permet une navigation à
+            partir de la "fin" de l'association. Deux sortes d'associations bidirectionnelles sont supportées :
+            <variablelist>
+                <varlistentry>
+                    <term>un-vers-plusieurs (NdT : one-to-many)</term>
+                    <listitem>
+                        <para>
+                            ensemble ou sac à une extrémité, une seule valeur à l'autre
+                        </para>
+                    </listitem>
+                </varlistentry>
+                <varlistentry>
+                    <term>plusieurs-vers-plusieurs (NdT : many-to-many)</term>
+                    <listitem>
+                        <para>
+                            ensemble ou sac aux deux extrémités
+                        </para>
+                    </listitem>
+                </varlistentry>
+            </variablelist>
+        </para>
+
+        <para>
+            Vous pouvez spécifier une association plusieurs-vers-plusieurs bidirectionnelle simplement
+            en mappant deux associations plusieurs-vers-plusieurs vers la même table de base de données et en déclarant une extrémité comme <emphasis>inverse</emphasis> (celle de votre choix, mais ça ne peut pas être une collection indexée).
+        </para>
+
+        <para>
+            Voici un exemple d'association bidirectionnelle plusieurs-vers-plusieurs ; chaque catégorie peut
+            avoir plusieurs objets et chaque objet peut être dans plusieurs catégories :
+        </para>
+
+        <programlisting><![CDATA[<class name="Category">
+    <id name="id" column="CATEGORY_ID"/>
+    ...
+    <bag name="items" table="CATEGORY_ITEM">
+        <key column="CATEGORY_ID"/>
+        <many-to-many class="Item" column="ITEM_ID"/>
+    </bag>
+</class>
+
+<class name="Item">
+    <id name="id" column="ITEM_ID"/>
+    ...
+
+    <!-- inverse end -->
+    <bag name="categories" table="CATEGORY_ITEM" inverse="true">
+        <key column="ITEM_ID"/>
+        <many-to-many class="Category" column="CATEGORY_ID"/>
+    </bag>
+</class>]]></programlisting>
+
+        <para>
+            Les changements faits uniquement sur l'extréminté inverse de l'association <emphasis>ne sont pas</emphasis>
+            persistés. Ceci signifie qu'Hibernate a deux représentations en mémoire pour chaque
+            association bidirectionnelles, un lien de A vers B et un autre de B vers A. C'est
+            plus facile à comprendre si vous pensez au modèle objet de Java et comment nous
+            créons une relation plusieurs-vers-plusieurs en Java :
+        </para>
+
+        <programlisting><![CDATA[
+category.getItems().add(item);          // La catégorie est maintenant "au courant" de la relation
+item.getCategories().add(category);     // L'objet est maintenant "au courant" de la relation
+
+session.persist(item);                   // La relation ne sera pas sauvegardée !
+session.persist(category);               // La relation sera sauvegardée]]></programlisting>
+
+        <para>
+            La partie non-inverse est utilisée pour sauvegarder la représentation en mémoire dans la base de données.
+        </para>
+
+        <para>
+            Vous pouvez définir une association un-vers-plusieurs bidirectionnelle en mappant une
+            association un-vers-plusieurs vers la(es) même(s) colonne(s) de table qu'une association
+            plusieurs-vers-un et en déclarant l'extrémité pluri-valuée <literal>inverse="true"</literal>.
+        </para>
+
+        <programlisting><![CDATA[<class name="Parent">
+    <id name="id" column="parent_id"/>
+    ....
+    <set name="children" inverse="true">
+        <key column="parent_id"/>
+        <one-to-many class="Child"/>
+    </set>
+</class>
+
+<class name="Child">
+    <id name="id" column="child_id"/>
+    ....
+    <many-to-one name="parent"
+        class="Parent"
+        column="parent_id"
+        not-null="true"/>
+</class>]]></programlisting>
+
+        <para>
+            Mapper une extrémité d'une association avec <literal>inverse="true"</literal> n'affecte
+            pas l'opération de cascades, ce sont des concepts orthogonaux !
+        </para>
+
+    </sect2>
+
+    <sect2 id="collections-indexedbidirectional">
+        <title>Associations bidirectionnelles avec des collections indexées</title>
+        <para>
+            Une association bidirectionnelle où une extrémité est représentée comme une <literal>&lt;list&gt;</literal>
+            ou une <literal>&lt;map&gt;</literal> requiert une considération spéciale. Si il y a une
+            propriété de la classe enfant qui mappe la colonne de l'index, pas de problème, nous pouvons
+            continuer à utiliser <literal>inverse="true"</literal> sur le mapping de la collection :
+        </para>
+
+        <programlisting><![CDATA[<class name="Parent">
+    <id name="id" column="parent_id"/>
+    ....
+    <map name="children" inverse="true">
+        <key column="parent_id"/>
+        <map-key column="name"
+            type="string"/>
+        <one-to-many class="Child"/>
+    </map>
+</class>
+
+<class name="Child">
+    <id name="id" column="child_id"/>
+    ....
+    <property name="name"
+        not-null="true"/>
+    <many-to-one name="parent"
+        class="Parent"
+        column="parent_id"
+        not-null="true"/>
+</class>]]></programlisting>
+
+        <para>
+            Mais, si il n'y a pas de telle prorpriété sur la classe enfant, nous ne pouvons pas penser
+            à l'association comme vraiment bidirectionnelle (il y a des informations disponibles à une
+            extrémité de l'association qui ne sont pas disponibles à l'autre extrémité). Dans ce cas,
+            nous ne pouvons pas mapper la collection <literal>inverse="true"</literal>. À la place, nous
+            pourrions utiliser le mapping suivant :
+        </para>
+
+        <programlisting><![CDATA[<class name="Parent">
+    <id name="id" column="parent_id"/>
+    ....
+    <map name="children">
+        <key column="parent_id"
+            not-null="true"/>
+        <map-key column="name"
+            type="string"/>
+        <one-to-many class="Child"/>
+    </map>
+</class>
+
+<class name="Child">
+    <id name="id" column="child_id"/>
+    ....
+    <many-to-one name="parent"
+        class="Parent"
+        column="parent_id"
+        insert="false"
+        update="false"
+        not-null="true"/>
+</class>]]></programlisting>
+
+       <para>
+           Notez que dans ce mapping, l'extrémité de l'association contenant la collection est responsable
+           des mises à jour de la clef étrangère. À faire : cela entraîne-t-il réellement des expressions
+           updates inutiles ?
+       </para>
+
+    </sect2>
+
+    <sect2 id="collections-ternary">
+        <title>Associations ternaires</title>
+
+        <para>
+            Il y a trois approches possibles pour mapper une association ternaire. L'une est d'utiliser
+            une <literal>Map</literal> avec une association en tant qu'index :
+        </para>
+
+        <programlisting><![CDATA[<map name="contracts">
+    <key column="employer_id" not-null="true"/>
+    <map-key-many-to-many column="employee_id" class="Employee"/>
+    <one-to-many class="Contract"/>
+</map>]]></programlisting>
+
+            <programlisting><![CDATA[<map name="connections">
+    <key column="incoming_node_id"/>
+    <map-key-many-to-many column="outgoing_node_id" class="Node"/>
+    <many-to-many column="connection_id" class="Connection"/>
+</map>]]></programlisting>
+
+        <para>
+            Une seconde approche est simplement de remodeler l'association comme une classe d'entité. C'est
+            l'approche la plus commune.
+        </para>
+
+        <para>
+            Une alternative finale est d'utiliser des éléments composites, dont nous discuterons plus tard.
+        </para>
+
+    </sect2>
+
+    <sect2 id="collections-idbag" revision="1">
+        <title>Utiliser un <literal>&lt;idbag&gt;</literal></title>
+
+        <para>
+            Si vous embrassez pleinement notre vue que les clefs composées sont une mauvaise
+            chose et que des entités devraient avoir des identifiants artificiels (des clefs
+            subrogées), alors vous pourriez trouver un peu curieux que les associations
+            plusieurs-vers-plusieurs et les collections de valeurs que nous avons montré jusqu'ici
+            mappent toutes des tables avec des clefs composées ! Maintenant, ce point est assez
+            discutable ; une table d'association pure ne semble pas beaucoup bénéficier d'une clef
+            subrogée (bien qu'une collection de valeur composées le <emphasis>pourrait</emphasis>).
+            Néanmoins, Hibernate fournit une foncionnalité qui vous permet de mapper
+            des associations plusieurs-vers-plusieurs et des collections de valeurs vers une
+            table avec une clef subrogée.
+        </para>
+
+        <para>
+            L'élément <literal>&lt;idbag&gt;</literal> vous laisse mapper une <literal>List</literal>
+            (ou une <literal>Collection</literal>) avec une sémantique de sac.
+        </para>
+
+<programlisting><![CDATA[<idbag name="lovers" table="LOVERS">
+    <collection-id column="ID" type="long">
+        <generator class="sequence"/>
+    </collection-id>
+    <key column="PERSON1"/>
+    <many-to-many column="PERSON2" class="Person" fetch="join"/>
+</idbag>]]></programlisting>
+
+        <para>
+            Comme vous pouvez voir, un <literal>&lt;idbag&gt;</literal> a un généréteur d'id
+            artificiel, comme une classe d'entité ! Une clef subrogée différente est assignée
+            à chaque ligne de la collection. Cependant, Hibernate ne fournit pas de mécanisme pour
+            découvrir la valeur d'une clef subrogée d'une ligne particulière.
+        </para>
+
+        <para>
+            Notez que les performances de la mise à jour d'un <literal>&lt;idbag&gt;</literal>
+            sont <emphasis>bien</emphasis> meilleures qu'un <literal>&lt;bag&gt;</literal> ordinaire !
+            Hibernate peut localiser des lignes individuelles efficacement et les mettre à jour ou
+            les effacer individuellement, comme une liste, une map ou un ensemble.
+        </para>
+
+        <para>
+            Dans l'implémentation actuelle, la stratégie de la génération de l'identifiant <literal>native</literal>
+            n'est pas supportée pour les identifiants de collection <literal>&lt;idbag&gt;</literal>.
+        </para>
+
+    </sect2>
+
+    </sect1>
+
+    <!--undocumenting this stuff -->
+
+    <!--sect1 id="collections-heterogeneous">
+        <title>Heterogeneous Associations</title>
+
+        <para>
+            The <literal>&lt;many-to-any&gt;</literal> and <literal>&lt;index-many-to-any&gt;</literal>
+            elements provide for true heterogeneous associations. These mapping elements work in the
+            same way as the <literal>&lt;any&gt;</literal> element - and should also be used
+            rarely, if ever.
+        </para>
+
+    </sect1-->
+
+    <sect1 id="collections-example" revision="1">
+        <title>Exemples de collections</title>
+
+        <para>
+            Les sections précédentes sont assez confuses. Donc prenons un exemple. Cette classe :
+        </para>
+
+        <programlisting><![CDATA[package eg;
+import java.util.Set;
+
+public class Parent {
+    private long id;
+    private Set children;
+
+    public long getId() { return id; }
+    private void setId(long id) { this.id=id; }
+
+    private Set getChildren() { return children; }
+    private void setChildren(Set children) { this.children=children; }
+
+    ....
+    ....
+}]]></programlisting>
+
+        <para>
+            a une collection d'instances de <literal>Child</literal>. Si chaque enfant
+            a au plus un parent, le mapping le plus naturel est une association
+            un-vers-plusieurs :
+        </para>
+
+        <programlisting><![CDATA[<hibernate-mapping>
+
+    <class name="Parent">
+        <id name="id">
+            <generator class="sequence"/>
+        </id>
+        <set name="children">
+            <key column="parent_id"/>
+            <one-to-many class="Child"/>
+        </set>
+    </class>
+
+    <class name="Child">
+        <id name="id">
+            <generator class="sequence"/>
+        </id>
+        <property name="name"/>
+    </class>
+
+</hibernate-mapping>]]></programlisting>
+
+        <para>
+            Ceci mappe les définitions de tables suivantes :
+        </para>
+
+        <programlisting><![CDATA[create table parent ( id bigint not null primary key )
+create table child ( id bigint not null primary key, name varchar(255), parent_id bigint )
+alter table child add constraint childfk0 (parent_id) references parent]]></programlisting>
+
+        <para>
+            Si le parent est <emphasis>requis</emphasis>, utilisez une association un-vers-plusieurs unidirectionnelle :
+        </para>
+
+        <programlisting><![CDATA[<hibernate-mapping>
+
+    <class name="Parent">
+        <id name="id">
+            <generator class="sequence"/>
+        </id>
+        <set name="children" inverse="true">
+            <key column="parent_id"/>
+            <one-to-many class="Child"/>
+        </set>
+    </class>
+
+    <class name="Child">
+        <id name="id">
+            <generator class="sequence"/>
+        </id>
+        <property name="name"/>
+        <many-to-one name="parent" class="Parent" column="parent_id" not-null="true"/>
+    </class>
+
+</hibernate-mapping>]]></programlisting>
+
+        <para>
+            Notez la contrainte <literal>NOT NULL</literal> :
+        </para>
+
+        <programlisting><![CDATA[create table parent ( id bigint not null primary key )
+create table child ( id bigint not null
+                     primary key,
+                     name varchar(255),
+                     parent_id bigint not null )
+alter table child add constraint childfk0 (parent_id) references parent]]></programlisting>
+
+        <para>
+            Alternativement, si vous insistez absolument pour que cette association soit unidirectionnelle,
+            vous pouvez déclarer la contrainte <literal>NOT NULL</literal> sur le mapping <literal>&lt;key&gt;</literal> :
+        </para>
+
+        <programlisting><![CDATA[<hibernate-mapping>
+
+    <class name="Parent">
+        <id name="id">
+            <generator class="sequence"/>
+        </id>
+        <set name="children">
+            <key column="parent_id" not-null="true"/>
+            <one-to-many class="Child"/>
+        </set>
+    </class>
+
+    <class name="Child">
+        <id name="id">
+            <generator class="sequence"/>
+        </id>
+        <property name="name"/>
+    </class>
+
+</hibernate-mapping>]]></programlisting>
+
+        <para>
+            D'un autre côté, si un enfant pouvait avoir plusieurs parent, une association
+            plusieurs-vers-plusieurs est plus appropriée :
+        </para>
+
+        <programlisting><![CDATA[<hibernate-mapping>
+
+    <class name="Parent">
+        <id name="id">
+            <generator class="sequence"/>
+        </id>
+        <set name="children" table="childset">
+            <key column="parent_id"/>
+            <many-to-many class="Child" column="child_id"/>
+        </set>
+    </class>
+
+    <class name="Child">
+        <id name="id">
+            <generator class="sequence"/>
+        </id>
+        <property name="name"/>
+    </class>
+
+</hibernate-mapping>]]></programlisting>
+
+        <para>
+            Définitions des tables :
+        </para>
+
+        <programlisting><![CDATA[create table parent ( id bigint not null primary key )
+create table child ( id bigint not null primary key, name varchar(255) )
+create table childset ( parent_id bigint not null,
+                        child_id bigint not null,
+                        primary key ( parent_id, child_id ) )
+alter table childset add constraint childsetfk0 (parent_id) references parent
+alter table childset add constraint childsetfk1 (child_id) references child]]></programlisting>
+
+        <para>
+            Pour plus d'exemples et une revue complète du mapping de la relation parent/enfant, voir
+            see <xref linkend="example-parentchild"/>.
+        </para>
+
+        <para>
+            Des mappings d'association plus exotiques sont possibles, nous cataloguerons toutes les possibilités
+            dans le prochain chapitre.
+        </para>
+
+    </sect1>
+
+</chapter>

Copied: core/trunk/documentation/manual/fr-FR/src/main/docbook/content/component_mapping.xml (from rev 14070, core/trunk/documentation/manual/fr-FR/src/main/docbook/modules/component_mapping.xml)
===================================================================
--- core/trunk/documentation/manual/fr-FR/src/main/docbook/content/component_mapping.xml	                        (rev 0)
+++ core/trunk/documentation/manual/fr-FR/src/main/docbook/content/component_mapping.xml	2007-10-09 18:28:36 UTC (rev 14074)
@@ -0,0 +1,402 @@
+<?xml version='1.0' encoding="iso-8859-1"?>
+<chapter id="components">
+    <title>Mapping de composants</title>
+
+    <para>
+        La notion de <emphasis>composants</emphasis> est réutilisé dans différents contextes,
+        avec différents objectifs, à travers Hibernate.
+    </para>
+
+    <sect1 id="components-dependentobjects" revision="2" >
+        <title>Objects dépendants</title>
+
+        <para>
+            Le composant est un objet inclu dans un autre qui est sauvegardé comme une valeur, et
+            non pas comme une entité.
+            Le composant fait référence à la notion (au sens objet) de composition
+            (et non pas de composant au sens d'architecture de composants).
+            Par exemple on pourrait modélisé l'objet personne de cette façon:
+        </para>
+
+        <programlisting><![CDATA[public class Person {
+    private java.util.Date birthday;
+    private Name name;
+    private String key;
+    public String getKey() {
+        return key;
+    }
+    private void setKey(String key) {
+        this.key=key;
+    }
+    public java.util.Date getBirthday() {
+        return birthday;
+    }
+    public void setBirthday(java.util.Date birthday) {
+        this.birthday = birthday;
+    }
+    public Name getName() {
+        return name;
+    }
+    public void setName(Name name) {
+        this.name = name;
+    }
+    ......
+    ......
+}]]></programlisting>
+
+<programlisting><![CDATA[public class Name {
+    char initial;
+    String first;
+    String last;
+    public String getFirst() {
+        return first;
+    }
+    void setFirst(String first) {
+        this.first = first;
+    }
+    public String getLast() {
+        return last;
+    }
+    void setLast(String last) {
+        this.last = last;
+    }
+    public char getInitial() {
+        return initial;
+    }
+    void setInitial(char initial) {
+        this.initial = initial;
+    }
+}]]></programlisting>
+
+        <para>
+            Maintenant <literal>Name</literal> peut-être sauvegardé comme un composant de 
+            <literal>Person</literal>. Remarquer que <literal>Name</literal> définit des methodes 
+            d'accès et de modification pour ses propriétés persistantes, mais il n'a pas besoin 
+            des interfaces ou des propriétés d'identification ( par exemple getId() ) qui sont propres aux entités.
+        </para>
+
+        <para>
+            Nous serions alors amené à mapper ce composant de cette façon:
+        </para>
+
+        <programlisting><![CDATA[<class name="eg.Person" table="person">
+    <id name="Key" column="pid" type="string">
+        <generator class="uuid"/>
+    </id>
+    <property name="birthday" type="date"/>
+    <component name="Name" class="eg.Name"> <!-- class attribute optional -->
+        <property name="initial"/>
+        <property name="first"/>
+        <property name="last"/>
+    </component>
+</class>]]></programlisting>
+
+        <para>
+            La table person aurai les colonnes <literal>pid</literal>,
+            <literal>birthday</literal>,
+            <literal>initial</literal>,
+            <literal>first</literal> and
+            <literal>last</literal>.
+        </para>
+
+        <para>
+            Comme tous les types valeurs, les composants ne supportent pas les références partagés.
+            En d'autres mots, deux instances de person peuvent avoir un même nom, mais ces noms sont
+			indépendants, ils peuvent être identiques si on les compare par valeur mais ils représentent
+			deux objets distincts en mémoire. La notion de nullité pour un composant est 
+            <emphasis>ad hoc</emphasis>. Quand il recharge l'objet qui contient le composant, Hibernate 
+            supposera que si tous les champs du composants sont nuls alors le composant sera positionné 
+            à la valeur null. Ce choix programmatif devrait être satisfaisant dans la plupart des cas.
+        </para>
+
+        <para>
+            Les propriétés d'un composant peuvent être de tous les types qu'Hibernate supporte habituellement
+            (collections, many-to-one associations, autres composants, etc). Les composants inclus ne doivent <emphasis>pas</emphasis> 
+            être vus comme quelque chose d'exotique. Hibernate a été conçu pour supporter un modèle objet très granulaire.
+        </para>
+
+        <para>
+            Le  <literal>&lt;component&gt;</literal> peut inclure dans la liste de ses propriétés
+            une référence au <literal>&lt;parent&gt;</literal> conteneur.
+        </para>
+
+        <programlisting><![CDATA[<class name="eg.Person" table="person">
+    <id name="Key" column="pid" type="string">
+        <generator class="uuid"/>
+    </id>
+    <property name="birthday" type="date"/>
+    <component name="Name" class="eg.Name" unique="true">
+        <parent name="namedPerson"/> <!-- référence arrière à Person -->
+        <property name="initial"/>
+        <property name="first"/>
+        <property name="last"/>
+    </component>
+</class>]]></programlisting>
+
+    </sect1>
+
+    <sect1 id="components-incollections" revision="1">
+        <title>Collection d'objets dépendants</title>
+
+        <para>
+            Les collections d'objets dépendants sont supportés (exemple: un tableau de type 
+            <literal>Name</literal>). Déclarer la collection de composants en remplaçant le tag <literal>&lt;element&gt;</literal> 
+            par le tag <literal>&lt;composite-element&gt;</literal>.
+        </para>
+
+        <programlisting><![CDATA[<set name="someNames" table="some_names" lazy="true">
+    <key column="id"/>
+    <composite-element class="eg.Name"> <!-- class attribute required -->
+        <property name="initial"/>
+        <property name="first"/>
+        <property name="last"/>
+    </composite-element>
+</set>]]></programlisting>
+
+        <para>
+            Remarque: Si vous définissez un <literal>Set</literal> d'élément composite,
+            il est très important d'implémenter la méthode <literal>equals()</literal> et 
+            <literal>hashCode()</literal> correctement.
+        </para>
+
+        <para>
+            Les élements composite peuvent aussi contenir des composants mais pas des collections.
+            Si votre élément composite contient aussi des composants, utilisez l'élément <literal>&lt;nested-composite-element&gt;</literal> 
+            . Une collections de composants qui ccontiennent eux-mêmes des composants est un cas très exotique.
+            A ce stade demandez-vous si une association un-à-plusieurs ne serait pas plus approprié.
+            Essayez de re remodeler votre élément composite comme une entité ( Dans ce cas même si le modèle
+            Java est le même la logique de persitence et de relation sont tout de même différentes)
+        </para>
+
+        <para>
+            Remarque, le mapping d'éléments composites ne supporte pas la nullité des 
+            propriétés lorsqu'on utilise un <literal>&lt;set&gt;</literal>. Hibernate
+            lorsqu'il supprime un objet utilise chaque colonne pour identifier un objet
+            (on ne peut pas utiliser des clés primaires distinctes dans une table d'éléments composites),
+            ce qui n'est pas possible avec des valeurs nulles. Vous devez donc choisir d'interdire la nullité
+            des propriétés d'un élément composite ou choisir un autre type de collection comme :
+            <literal>&lt;list&gt;</literal>, <literal>&lt;map&gt;</literal>,
+            <literal>&lt;bag&gt;</literal> ou <literal>&lt;idbag&gt;</literal>.
+        </para>
+
+        <para>
+            Un cas particulier d'élément composite est un élément composite qui inclut un élément
+            <literal>&lt;many-to-one&gt;</literal>. Un mapping comme celui-ci 
+            vous permet d'associer les colonnes d'une table d'association plusieurs à plusieurs (many-to-many)
+            à la classse de l'élément composite. L'exemple suivant est une association plusieurs à plusieurs
+            de <literal>Order</literal> à <literal>Item</literal> à 
+            <literal>purchaseDate</literal>, <literal>price</literal> et
+            <literal>quantity</literal> sont des propriétés de l'association.
+        </para>
+
+        <programlisting><![CDATA[<class name="eg.Order" .... >
+    ....
+    <set name="purchasedItems" table="purchase_items" lazy="true">
+        <key column="order_id">
+        <composite-element class="eg.Purchase">
+            <property name="purchaseDate"/>
+            <property name="price"/>
+            <property name="quantity"/>
+            <many-to-one name="item" class="eg.Item"/> <!-- class attribute is optional -->
+        </composite-element>
+    </set>
+</class>]]></programlisting>
+
+        <para>
+            Bien sûr, il ne peut pas y avoir de référence à l'achat (purchase) depuis l'article (item), pour 
+            pouvoir naviguer de façon bidirectionnelle dans l'association. N'oubliez pas que les composants 
+            sont de type valeurs et n'autorise pas les références partagées. 
+        </para>
+
+        <para>Même les associations ternaires ou quaternaires sont possibles:</para>
+
+        <programlisting><![CDATA[<class name="eg.Order" .... >
+    ....
+    <set name="purchasedItems" table="purchase_items" lazy="true">
+        <key column="order_id">
+        <composite-element class="eg.OrderLine">
+            <many-to-one name="purchaseDetails class="eg.Purchase"/>
+            <many-to-one name="item" class="eg.Item"/>
+        </composite-element>
+    </set>
+</class>]]></programlisting>
+
+        <para>
+            Les éléments composites peuvent apparaître dans les requêtes en utilisant
+            la même syntaxe que associations
+        </para>
+
+    </sect1>
+
+    <sect1 id="components-asmapindex">
+        <title>Utiliser les composants comme index de map</title>
+
+        <para>
+            l'élément <literal>&lt;composite-map-key&gt;</literal> 
+            vous permet d'utiliser une classe de composant comme indice de 
+            <literal>Map</literal>. Assurez-vous d'avoir surdéfini 
+            <literal>hashCode()</literal> et <literal>equals()</literal> dans la 
+            classe du composant.
+        </para>
+    </sect1>
+
+    <sect1 id="components-compositeid" revision="1">
+        <title>Utiliser un composant comme identifiant</title>
+
+        <para>
+            Vous pouvez utiliser un composant comme identifiant d'une entité.
+            Mais pour cela la classe du composant doit respecter certaines règles.
+        </para>
+
+        <itemizedlist spacing="compact">
+            <listitem>
+                <para>
+                    Elle doit implémenter <literal>java.io.Serializable</literal>.
+                </para>
+            </listitem>
+            <listitem>
+                <para>
+                    Elle doit redéfinir <literal>equals()</literal> et
+                    <literal>hashCode()</literal>, de façon cohérente avec le 
+                    fait qu'elle définit une clé composite dans la base de 
+                    données.
+                </para>
+            </listitem>
+        </itemizedlist>
+        
+        <para>
+            <emphasis>
+            Remarque: avec hibernate3, la seconde règle n'est plus absolument 
+            necessaire mais faîtes le quand même.</emphasis>
+        </para>
+
+        <para>
+        	Vous ne pouvez pas utiliser de <literal>IdentifierGenerator</literal> pour générer 
+        	une clé composite, l'application devra définir elle même ses propres identifiants.
+        </para>
+
+        <para>
+            Utiliser l'élément <literal>&lt;composite-id&gt;</literal>  (en incluant l'élément 
+            <literal>&lt;key-property&gt;</literal>) à la place de l'habituel déclaration 
+            <literal>&lt;id&gt;</literal>. Par exemple la classe
+            <literal>OrderLine</literal> qui dépend de la clé primaire 
+             (composite) de  <literal>Order</literal>.
+        </para>
+
+        <programlisting><![CDATA[<class name="OrderLine">
+    
+    <composite-id name="id" class="OrderLineId">
+        <key-property name="lineId"/>
+        <key-property name="orderId"/>
+        <key-property name="customerId"/>
+    </composite-id>
+    
+    <property name="name"/>
+    
+    <many-to-one name="order" class="Order"
+            insert="false" update="false">
+        <column name="orderId"/>
+        <column name="customerId"/>
+    </many-to-one>
+    ....
+    
+</class>]]></programlisting>
+
+        <para>
+            Maintenant toutes clés étrangères référençant la table <literal>OrderLine</literal> 
+            devra aussi être composite. Vous devez en tenir compte lorsque vous écrivez vos mapping d'association pour les autres classes.
+            Une association à <literal>OrderLine</literal> devrait être mappé de la façon suivante :
+        </para>
+
+        <programlisting><![CDATA[<many-to-one name="orderLine" class="OrderLine">
+<!-- the "class" attribute is optional, as usual -->
+    <column name="lineId"/>
+    <column name="orderId"/>
+    <column name="customerId"/>
+</many-to-one>]]></programlisting>
+
+        <para>
+            (Remarque: l'élément <literal>&lt;column&gt;</literal> est une alternative à l'attribut 
+            <literal>column</literal> que l'on utilise partout.) 
+        </para>
+        
+        <para>
+            Une association <literal>plusieurs-à-plusieurs</literal> (many-to-many) à <literal>OrderLine</literal> 
+            utilisera aussi une clé étrangère composite:
+        </para>
+    
+    <programlisting><![CDATA[<set name="undeliveredOrderLines">
+    <key column name="warehouseId"/>
+    <many-to-many class="OrderLine">
+        <column name="lineId"/>
+        <column name="orderId"/>
+        <column name="customerId"/>
+    </many-to-many>
+</set>]]></programlisting>
+
+        <para>
+            La collection des <literal>OrderLine</literal>s dans <literal>Order</literal>
+            utilisera:
+        </para>
+
+    <programlisting><![CDATA[<set name="orderLines" inverse="true">
+    <key>
+        <column name="orderId"/>
+        <column name="customerId"/>
+    </key>
+    <one-to-many class="OrderLine"/>
+</set>]]></programlisting>
+
+        <para>
+            (L'élément <literal>&lt;one-to-many&gt;</literal>, comme d'habitude, ne déclare pas de colonne.)
+        </para>
+        
+        <para>
+            Si <literal>OrderLine</literal> lui-même possède une collection, celle-ci aura aussi 
+            une clé composite étrangère.
+        </para>
+
+        <programlisting><![CDATA[<class name="OrderLine">
+    ....
+    ....
+    <list name="deliveryAttempts">
+        <key>   <!-- a collection inherits the composite key type -->
+            <column name="lineId"/>
+            <column name="orderId"/>
+            <column name="customerId"/>
+        </key>
+        <list-index column="attemptId" base="1"/>
+        <composite-element class="DeliveryAttempt">
+            ...
+        </composite-element>
+    </set>
+</class>]]></programlisting>
+
+    </sect1>
+
+    <sect1 id="components-dynamic" revision="1">
+        <title>Composant Dynamique</title>
+
+        <para>
+            Vous pouvez même mapper une propriété de type <literal>Map</literal>:
+        </para>
+
+    <programlisting><![CDATA[<dynamic-component name="userAttributes">
+    <property name="foo" column="FOO"/>
+    <property name="bar" column="BAR"/>
+    <many-to-one name="baz" class="Baz" column="BAZ_ID"/>
+</dynamic-component>]]></programlisting>
+
+        <para>
+            La sémantique de l'association à un <literal>&lt;dynamic-component&gt;</literal>
+            est identique à celle que l'on utilise pour les composants.
+            L'avantage de ce type de mapping est qu'il pemet de déterminer les véritables propriétés 
+            du bean au moment su déploiement en éditant simplement le document de mapping.
+            La manipulation du document de mapping pendant l'execution de l'application est aussi 
+            possible en utilisant un parser DOM. Il ya même mieux, vous pouvez accéder (et changer)
+            le metamodel de configuration d'hibernate en utilisant l'objet <literal>Configuration</literal>            
+        </para>
+
+    </sect1>
+
+</chapter>

Copied: core/trunk/documentation/manual/fr-FR/src/main/docbook/content/configuration.xml (from rev 14070, core/trunk/documentation/manual/fr-FR/src/main/docbook/modules/configuration.xml)
===================================================================
--- core/trunk/documentation/manual/fr-FR/src/main/docbook/content/configuration.xml	                        (rev 0)
+++ core/trunk/documentation/manual/fr-FR/src/main/docbook/content/configuration.xml	2007-10-09 18:28:36 UTC (rev 14074)
@@ -0,0 +1,1759 @@
+<?xml version='1.0' encoding="iso-8859-1"?>
+<chapter id="session-configuration" revision="1">
+
+    <title>Configuration</title>
+    
+    <para>
+        Parce qu'Hibernate est conçu pour fonctionner dans différents environnements,
+        il existe beaucoup de paramètres de configuration. Heureusement, la plupart
+        ont des valeurs par défaut appropriées et la distribution d'Hibernate contient
+        un exemple de fichier <literal>hibernate.properties</literal> dans le répertoire
+        <literal>etc/</literal> qui montre les différentes options. Vous n'avez qu'à 
+        placer ce fichier dans votre classpath et à l'adapter.
+    </para>
+
+    <sect1 id="configuration-programmatic" revision="1">
+        <title>Configuration par programmation</title>
+
+        <para>
+            Une instance de <literal>org.hibernate.cfg.Configuration</literal>
+            représente un ensemble de mappings des classes Java d'une application vers
+            la base de données SQL. La <literal>Configuration</literal> est utilisée
+            pour construire un objet (immuable) <literal>SessionFactory</literal>.
+            Les mappings sont constitués d'un ensemble de fichiers de mapping XML.
+        </para>
+
+        <para>
+            Vous pouvez obtenir une instance de <literal>Configuration</literal>
+            en l'instanciant directement et en spécifiant la liste des documents 
+            XML de mapping. Si les fichiers de mapping sont dans le classpath, vous
+            pouvez le faire à l'aide de la méthode <literal>addResource()</literal> :
+        </para>
+
+        <programlisting><![CDATA[Configuration cfg = new Configuration()
+    .addResource("Item.hbm.xml")
+    .addResource("Bid.hbm.xml");]]></programlisting>
+
+        <para>
+            Une alternative (parfois meilleure)  est de spécifier les classes mappées
+            et de laisser Hibernate trouver les documents de mapping pour vous :
+        </para>
+
+        <programlisting><![CDATA[Configuration cfg = new Configuration()
+    .addClass(org.hibernate.auction.Item.class)
+    .addClass(org.hibernate.auction.Bid.class);]]></programlisting>
+
+        <para>
+            Hibernate va rechercher les fichiers de mappings 
+            <literal>/org/hibernate/auction/Item.hbm.xml</literal> et
+            <literal>/org/hibernate/auction/Bid.hbm.xml</literal> dans le classpath.
+            Cette approche élimine les noms de fichiers en dur.
+        </para>
+        
+        <para>
+            Une <literal>Configuration</literal> vous permet également de préciser des
+            propriétés de configuration :
+        </para>
+
+        <programlisting><![CDATA[Configuration cfg = new Configuration()
+    .addClass(org.hibernate.auction.Item.class)
+    .addClass(org.hibernate.auction.Bid.class)
+    .setProperty("hibernate.dialect", "org.hibernate.dialect.MySQLInnoDBDialect")
+    .setProperty("hibernate.connection.datasource", "java:comp/env/jdbc/test")
+    .setProperty("hibernate.order_updates", "true");]]></programlisting>
+
+        <para>
+            Ce n'est pas le seul moyen de passer des propriétés de configuration à Hibernate.
+            Les différentes options sont :
+        </para>
+
+        <orderedlist spacing="compact">
+            <listitem>
+                <para>
+                    Passer une instance de <literal>java.util.Properties</literal>
+                    à <literal>Configuration.setProperties()</literal>.
+                </para>
+            </listitem>
+            <listitem>
+                <para>
+                    Placer <literal>hibernate.properties</literal> dans un répertoire racine
+                    du classpath
+                </para>
+            </listitem>
+            <listitem>
+                <para>
+                    Positionner les propriétés <literal>System</literal> en utilisant
+                    <literal>java -Dproperty=value</literal>.
+                </para>
+            </listitem>
+            <listitem>
+                <para>
+                    Inclure des éléments <literal>&lt;property&gt;</literal> dans le
+                    fichier <literal>hibernate.cfg.xml</literal> (voir plus loin).
+                </para>
+            </listitem>
+        </orderedlist>
+
+        <para>
+            L'utilisation d'<literal>hibernate.properties</literal> est l'approche la plus
+            simple si vous voulez démarrer rapidement
+        </para>
+        <para>
+            La <literal>Configuration</literal> est un objet de démarrage qui sera supprimé
+            une fois qu'une <literal>SessionFactory</literal> aura été créée.
+        </para>
+
+    </sect1>
+    
+    <sect1 id="configuration-sessionfactory">
+        <title>Obtenir une SessionFactory</title>
+
+        <para>
+            Une fois que tous les mappings ont été parsés par la <literal>Configuration</literal>, 
+            l'application doit obtenir une fabrique d'instances de <literal>Session</literal>. 
+            Cette fabrique sera partagée entre tous les threads de l'application :
+        </para>
+
+        <programlisting><![CDATA[SessionFactory sessions = cfg.buildSessionFactory();]]></programlisting>
+
+        <para>
+            Hibernate permet à votre application d'instancier plus d'une <literal>SessionFactory</literal>.
+            Cela est pratique lorsque vous utilisez plus d'une base de données.
+        </para>
+
+    </sect1>
+
+    <sect1 id="configuration-hibernatejdbc" revision="1">
+        <title>Connexions JDBC</title>
+
+        <para>
+            Habituellement, vous voulez que la <literal>SessionFactory</literal> crée les connexions JDBC et
+            les mette dans un pool pour vous. Si vous suivez cette approche, ouvrir une <literal>Session</literal> 
+            est aussi simple que :
+        </para>
+
+        <programlisting><![CDATA[Session session = sessions.openSession(); // open a new Session]]></programlisting>
+        
+        <para>
+            Dès que vous ferez quelquechose qui requiert un accès à la base de données, une connexion
+            JDBC sera récupérée dans le pool.
+        </para>
+
+        <para>
+            Pour faire cela, il faut passer les propriétés de la connexion JDBC à Hibernate.
+            Tous les noms des propriétés Hibernate et leur signification sont définies dans
+            la classe <literal>org.hibernate.cfg.Environment</literal>. Nous allons maintenant
+            décrire les paramètres de configuration des connexions JDBC les plus importants.
+        </para>
+
+         <para>
+            Hibernate obtiendra des connexions (et les mettra dans un pool) en utilisant 
+            <literal>java.sql.DriverManager</literal> si vous positionnez les paramètres de la manière
+            suivante :
+        </para>
+
+        <table frame="topbot">
+            <title>Propriétés JDBC d'Hibernate</title>
+            <tgroup cols="2">
+                <colspec colname="c1" colwidth="1*"/>
+                <colspec colname="c2" colwidth="1*"/>
+                <thead>
+                    <row>
+                        <entry>Nom de la propriété</entry>
+                        <entry>Fonction</entry>
+                    </row>
+                </thead>
+            <tbody>
+            <row>
+                <entry>
+                    <literal>hibernate.connection.driver_class</literal>
+                </entry>
+                <entry>
+                    <emphasis>Classe du driver jdbc</emphasis>
+                </entry>
+            </row>
+            <row>
+                <entry>
+                    <literal>hibernate.connection.url</literal>
+                </entry>
+                <entry>
+                    <emphasis>URL jdbc</emphasis>
+                </entry>
+            </row>
+            <row>
+                <entry>
+                    <literal>hibernate.connection.username</literal>
+                </entry>
+                <entry>
+                    <emphasis>utilisateur de la base de données</emphasis>
+                </entry>
+            </row>
+            <row>
+                <entry>
+                    <literal>hibernate.connection.password</literal>
+                </entry>
+                <entry>
+                    <emphasis>mot de passe de la base de données</emphasis>
+                </entry>
+            </row>
+            <row>
+                <entry>
+                    <literal>hibernate.connection.pool_size</literal>
+                </entry>
+                <entry>
+                    <emphasis>nombre maximum de connexions dans le pool</emphasis>
+                </entry>
+            </row>
+            </tbody>
+            </tgroup>
+        </table>
+
+        <para>
+            L'algorithme natif de pool de connexions d'Hibernate est plutôt rudimentaire. Il a été fait 
+            dans le but de vous aider à démarrer et <emphasis>n'est pas prévu pour un système en production</emphasis>
+            ou même pour un test de peformance. Utilisez plutôt un pool tiers pour de meilleures performances et une
+            meilleure stabilité : pour cela, remplacez la propriété <literal>hibernate.connection.pool_size</literal> avec les propriétés
+            spécifique au pool de connexions que vous avez choisi. Cela désactivera le pool de connexions interne
+            d'Hibernate. Vous pouvez par exemple utiliser C3P0.
+        </para>
+
+        <para>
+            C3P0 est un pool de connexions JDBC open source distribué avec Hibernate dans le répertoire
+            <literal>lib</literal>. Hibernate utilisera son provider <literal>C3P0ConnectionProvider</literal>
+            pour le pool de connexions si vous positionnez les propriétés <literal>hibernate.c3p0.*</literal>.
+            Si vous voulez utiliser Proxool, référez vous au groupe de propriétés d'<literal>hibernate.properties</literal>
+            correspondant et regardez sur le site web d'Hibernate pour plus d'informations.
+        </para>
+
+        <para>
+            Voici un exemple de fichier <literal>hibernate.properties</literal> pour C3P0:
+        </para>
+
+        <programlisting id="c3p0-configuration" revision="1"><![CDATA[hibernate.connection.driver_class = org.postgresql.Driver
+hibernate.connection.url = jdbc:postgresql://localhost/mydatabase
+hibernate.connection.username = myuser
+hibernate.connection.password = secret
+hibernate.c3p0.min_size=5
+hibernate.c3p0.max_size=20
+hibernate.c3p0.timeout=1800
+hibernate.c3p0.max_statement=50
+hibernate.dialect = org.hibernate.dialect.PostgreSQLDialect]]></programlisting>
+
+        <para>
+            Dans le cadre de l'utilisation au sein d'un serveur d'applications,
+            vous devriez quasiment toujours configurer Hibernate pour qu'il obtienne
+            ses connexions de la <literal>DataSource</literal> du serveur d'application
+            enregistrée dans le JNDI. Pour cela vous devrez définir au moins une des
+            propriétés suivantes :
+        </para>
+
+        <table frame="topbot">
+            <title>Propriété d'une Datasource Hibernate</title>
+            <tgroup cols="2">
+                <colspec colname="c1" colwidth="1*"/>
+                <colspec colname="c2" colwidth="1*"/>
+                <thead>
+                    <row>
+                        <entry>Nom d'une propriété</entry>
+                        <entry>fonction</entry>
+                    </row>
+                </thead>
+            <tbody>
+            <row>
+                <entry>
+                    <literal>hibernate.connection.datasource</literal>
+                </entry>
+                <entry>
+                    <emphasis>Nom JNDI de la datasource</emphasis>
+                </entry>
+            </row>
+            <row>
+                <entry>
+                    <literal>hibernate.jndi.url</literal>
+                </entry>
+                <entry>
+                    <emphasis>URL du fournisseur JNDI</emphasis> (optionnelle)
+                </entry>
+            </row>
+            <row>
+                <entry>
+                    <literal>hibernate.jndi.class</literal>
+                </entry>
+                <entry>
+                    <emphasis>Classe de l'<literal>InitialContextFactory</literal> du JNDI</emphasis> (optionnelle)
+                </entry>
+            </row>
+            <row>
+                <entry>
+                    <literal>hibernate.connection.username</literal>
+                </entry>
+                <entry>
+                    <emphasis>utilisateur de la base de données</emphasis> (optionnelle)
+                </entry>
+            </row>
+            <row>
+                <entry>
+                    <literal>hibernate.connection.password</literal>
+                </entry>
+                <entry>
+                    <emphasis>mot de passe de la base de données</emphasis> (optionnelle)
+                </entry>
+            </row>
+            </tbody>
+            </tgroup>
+        </table>
+
+        <para>
+            Voici un exemple de fichier <literal>hibernate.properties</literal>
+            pour l'utilisation d'une datasource JNDI fournie par un serveur d'applications :
+        </para>
+
+        <programlisting><![CDATA[hibernate.connection.datasource = java:/comp/env/jdbc/test
+hibernate.transaction.factory_class = \
+    org.hibernate.transaction.JTATransactionFactory
+hibernate.transaction.manager_lookup_class = \
+    org.hibernate.transaction.JBossTransactionManagerLookup
+hibernate.dialect = org.hibernate.dialect.PostgreSQLDialect]]></programlisting>
+
+        <para>
+            Les connexions JDBC obtenues à partir d'une datasource JNDI participeront automatiquement
+            aux transactions gérées par le conteneur du serveur d'applications.
+        </para>
+
+        <para>
+            Des propriétés supplémentaires de connexion peuvent être passées en préfixant
+            le nom de la propriété par "<literal>hibernate.connnection</literal>". Par exemple,
+            vous pouvez spécifier un jeu de caractères en utilisant 
+            <literal>hibernate.connection.charSet</literal>.
+        </para>
+
+        <para>
+            Vous pouvez fournir votre propre stratégie d'obtention des connexions JDBC en implémentant l'interface
+            <literal>org.hibernate.connection.ConnectionProvider</literal>. Vous pouvez sélectionner
+            une implémentation spécifique en positionnant <literal>hibernate.connection.provider_class</literal>.
+        </para>
+
+    </sect1>
+
+    <sect1 id="configuration-optional" revision="1">
+        <title>Propriétés de configuration optionnelles</title>
+        
+        <para>
+            Il y a un certain nombre d'autres propriétés qui contrôlent le fonctionnement 
+            d'Hibernate à l'exécution. Toutes sont optionnelles et ont comme valeurs par défaut
+            des valeurs "raisonnables" pour un fonctionnement nominal.
+        </para>
+
+        <para>
+            <emphasis>Attention : Certaines de ces propriétés sont uniquement de niveau System.</emphasis>
+            Les propriétés de niveau System ne peuvent être positionnées que via la ligne de commande
+            (<literal>java -Dproperty=value</literal>) ou être définies dans <literal>hibernate.properties</literal>.
+            Elle <emphasis>ne peuvent pas</emphasis> l'être via une des autres techniques décrites ci-dessus.
+        </para>
+
+        <table frame="topbot" id="configuration-optional-properties" revision="8">
+            <title>Propriétés de configuration d'Hibernate</title>
+            <tgroup cols="2">
+                <colspec colname="c1" colwidth="1*"/>
+                <colspec colname="c2" colwidth="1*"/>
+                <thead>
+                    <row>
+                        <entry>Nom de la propriété</entry>
+                        <entry>Fonction</entry>
+                    </row>
+                </thead>
+                <tbody>
+                    <row>
+                        <entry>
+                            <literal>hibernate.dialect</literal>
+                        </entry>
+                        <entry>
+                            Le nom de la classe du <literal>Dialect</literal> Hibernate.
+                            qui permet à Hibernate de générer du SQL optimisé pour une
+                            base de données relationnelle particulière.
+                            <para>
+                                <emphasis role="strong">ex.</emphasis> 
+                                <literal>nom.complet.de.ma.classe.de.Dialect</literal>
+                            </para>
+                        </entry>
+                    </row>
+                    <row>
+                        <entry>
+                            <literal>hibernate.show_sql</literal>
+                        </entry>
+                        <entry>
+                            Ecrit toutes les requêtes SQL sur la console. Il s'agit d'une
+                            alternative au positionnement de la catégorie de log
+                            <literal>org.hibernate.SQL</literal> au niveau <literal>debug</literal>.
+                            <para>
+                                <emphasis role="strong">ex.</emphasis> 
+                                <literal>true</literal> | <literal>false</literal>
+                            </para>
+                        </entry>
+                    </row>
+                    <row>
+                        <entry>
+                            <literal>hibernate.format_sql</literal>
+                        </entry>
+                        <entry>
+                            Formate et indente le sql dans la console et dans le log
+                            <para>
+                                <emphasis role="strong">ex.</emphasis> 
+                                <literal>true</literal> | <literal>false</literal>
+                            </para>
+                        </entry>
+                    </row>
+                    <row>
+                        <entry>
+                            <literal>hibernate.default_schema</literal>
+                        </entry>
+                        <entry>
+                            Positionne dans le SQL généré un schéma/tablespace par défaut pour les noms de
+                            table ne l'ayant pas surchargé.
+                            <para>
+                                <emphasis role="strong">ex.</emphasis> 
+                                <literal>MON_SCHEMA</literal>
+                            </para>
+                        </entry>
+                    </row>
+                    <row>
+                        <entry>
+                            <literal>hibernate.default_catalog</literal>
+                        </entry>
+                        <entry>
+                            Qualifie les noms de tables non qualifiées avec ce catalogue
+                            dans le SQL généré.
+                            <para>
+                                <emphasis role="strong">ex.</emphasis> 
+                                <literal>CATALOG_NAME</literal>
+                            </para>
+                        </entry>
+                    </row>
+                    <row>
+                        <entry>
+                            <literal>hibernate.session_factory_name</literal>
+                        </entry>
+                        <entry>
+                            La <literal>SessionFactory</literal> sera automatiquement
+                            liée à ce nom dans le JNDI après sa création.
+                            <para>
+                                <emphasis role="strong">ex.</emphasis> 
+                                <literal>jndi/nom/hierarchique</literal>
+                            </para>
+                        </entry>
+                    </row>
+                    <row>
+                        <entry>
+                            <literal>hibernate.max_fetch_depth</literal>
+                        </entry>
+                        <entry>
+                            Définit la profondeur maximale d'un arbre de chargement par
+                            jointures ouvertes pour les associations à cardinalité unitaire
+                            (un-à-un, plusieurs-à-un).
+                            Un <literal>0</literal> désactive le chargement par jointure
+                            ouverte.
+                            <para>
+                                <emphasis role="strong">ex.</emphasis> 
+                                valeurs recommandées entre <literal>0</literal> et <literal>3</literal>
+                            </para>
+                        </entry>
+                    </row>
+                    <row>
+                        <entry>
+                            <literal>hibernate.default_batch_fetch_size</literal>
+                        </entry>
+                        <entry>
+                            Définit une taille par défaut pour le chargement par lot des associations
+                            <para>
+                                <emphasis role="strong">ex.</emphasis> 
+                                Valeurs recommandées : <literal>4</literal>, <literal>8</literal>, 
+                                <literal>16</literal>
+                            </para>
+                        </entry>
+                    </row>
+                    <row>
+                        <entry>
+                            <literal>hibernate.default_entity_mode</literal>
+                        </entry>
+                        <entry>
+                            Définit un mode de représentation par défaut des entités pour
+                            toutes les sessions ouvertes depuis cette <literal>SessionFactory</literal>
+                            <para>
+                                <literal>dynamic-map</literal>, <literal>dom4j</literal>,
+                                <literal>pojo</literal>
+                            </para>
+                        </entry>
+                    </row>
+                    <row>
+                        <entry>
+                            <literal>hibernate.order_updates</literal>
+                        </entry>
+                        <entry>
+                            Force Hibernate à trier les updates SQL par la valeur de la clé
+                            primaire des éléments qui sont mis à jour. Cela permet de limiter
+                            les deadlocks de transaction dans les systèmes hautement concurents.
+                            <para>
+                                <emphasis role="strong">ex.</emphasis> 
+                                <literal>true</literal> | <literal>false</literal>
+                            </para>
+                        </entry>
+                    </row>
+                    <row>
+                        <entry>
+                            <literal>hibernate.generate_statistics</literal>
+                        </entry>
+                        <entry>
+                            Si activé, Hibernate va collecter des statistiques utiles
+                            pour le réglage des performances.
+                            <para>
+                                <emphasis role="strong">ex.</emphasis>
+                                <literal>true</literal> | <literal>false</literal>
+                            </para>
+                        </entry>
+                    </row>
+                    <row>
+                        <entry>
+                            <literal>hibernate.use_identifer_rollback</literal>
+                        </entry>
+                        <entry>
+                            Si activé, les propriétés correspondant à l'identifiant
+                            des objets vont être remises aux valeurs par défaut lorsque
+                            les objets seront supprimés.
+                            <para>
+                                <emphasis role="strong">ex.</emphasis>
+                                <literal>true</literal> | <literal>false</literal>
+                            </para>
+                        </entry>
+                    </row>
+                    <row>
+                        <entry>
+                            <literal>hibernate.use_sql_comments</literal>
+                        </entry>
+                        <entry>
+                            Si activé, Hibernate va générer des commentaires à l'intérieur
+                            des requêtes SQL pour faciliter le debogage., par défaut à <literal>false</literal>.
+                            <para>
+                                <emphasis role="strong">ex.</emphasis>
+                                <literal>true</literal> | <literal>false</literal>
+                            </para>
+                        </entry>
+                    </row>
+                </tbody>
+            </tgroup>
+        </table>
+
+         <table frame="topbot" id="configuration-jdbc-properties" revision="8">
+            <title>Propriétés Hibernate liées à JDBC et aux connexions</title>
+            <tgroup cols="2">
+                <colspec colname="c1" colwidth="1*"/>
+                <colspec colname="c2" colwidth="1*"/>
+                <thead>
+                    <row>
+                        <entry>Nom de la propriété</entry>
+                        <entry>Fonction</entry>
+                    </row>
+                </thead>
+                <tbody>
+                    <row>
+                        <entry>
+                            <literal>hibernate.jdbc.fetch_size</literal>
+                        </entry>
+                        <entry>
+                            Une valeur non nulle détermine la taille de chargement
+                            des statements JDBC (appelle 
+                            <literal>Statement.setFetchSize()</literal>).
+                        </entry>
+                    </row>
+                    <row>
+                        <entry>
+                            <literal>hibernate.jdbc.batch_size</literal>
+                        </entry>
+                        <entry>
+                            Une valeur non nulle active l'utilisation par Hibernate des mises 
+                            à jour par batch de JDBC2.
+                            <para>
+                                <emphasis role="strong">ex.</emphasis> 
+                                les valeurs recommandées entre <literal>5</literal> et <literal>30</literal>
+                            </para>
+                        </entry>
+                    </row>
+                    <row>
+                        <entry>
+                            <literal>hibernate.jdbc.batch_versioned_data</literal>
+                        </entry>
+                        <entry>
+                            Paramétrez cette propriété à <literal>true</literal> si votre pilote JDBC
+                            retourne des row counts corrects depuis <literal>executeBatch()</literal> (il est 
+                            souvent approprié d'activer cette option). Hibernate utilisera alors le "batched DML" pour
+                            versionner automatiquement les données. Par défaut = <literal>false</literal>.
+                            <para>
+                                <emphasis role="strong">eg.</emphasis>
+                                <literal>true</literal> | <literal>false</literal>
+                            </para>
+                        </entry>
+                    </row>
+                    <row>
+                        <entry>
+                            <literal>hibernate.jdbc.factory_class</literal>
+                        </entry>
+                        <entry>
+                           Sélectionne un <literal>Batcher</literal> personnalisé. La
+                           plupart des applications n'auront pas besoin de cette propriété
+                           de configuration
+                            <para>
+                                <emphasis role="strong">ex.</emphasis>
+                                <literal>classname.of.BatcherFactory</literal>
+                            </para>
+                        </entry>
+                    </row>
+                    <row>
+                        <entry>
+                            <literal>hibernate.jdbc.use_scrollable_resultset</literal>
+                        </entry>
+                        <entry>
+                            Active l'utilisation par Hibernate des resultsets scrollables 
+                            de JDBC2. Cette propriété est seulement nécessaire lorsque l'on
+                            utilise une connexion JDBC fournie par l'utilisateur. Autrement,
+                            Hibernate utilise les métadonnées de la connexion.
+                            <para>
+                                <emphasis role="strong">ex.</emphasis> 
+                                <literal>true</literal> | <literal>false</literal>
+                            </para>
+                        </entry>
+                    </row>
+                    <row>
+                        <entry>
+                            <literal>hibernate.jdbc.use_streams_for_binary</literal>
+                        </entry>
+                        <entry>
+                            Utilise des flux lorsque l'on écrit/lit des types
+                            <literal>binary</literal> ou <literal>serializable</literal>
+                            vers et à partir de JDBC (propriété de niveau système).
+                            <para>
+                                <emphasis role="strong">ex.</emphasis>
+                                <literal>true</literal> | <literal>false</literal>
+                            </para>
+                        </entry>
+                    </row>
+                    <row>
+                        <entry>
+                            <literal>hibernate.jdbc.use_get_generated_keys</literal>
+                        </entry>
+                        <entry>
+                            Active l'utilisation de <literal>PreparedStatement.getGeneratedKeys()</literal> de JDBC3
+                            pour récupérer nativement les clés générées après insertion. Nécessite un pilote
+                            JDBC3+, le mettre à false si votre pilote a des problèmes avec les générateurs
+                            d'identifiant Hibernate. Par défaut, essaie de déterminer les possibilités du
+                            pilote en utilisant les meta données de connexion.
+                            <para>
+                                <emphasis role="strong">eg.</emphasis>
+                                <literal>true|false</literal>
+                            </para>
+                        </entry>
+                    </row>                    
+                    <row>
+                        <entry>
+                            <literal>hibernate.connection.provider_class</literal>
+                        </entry>
+                        <entry>
+                            Le nom de la classe d'un <literal>ConnectionProvider</literal> personnalisé
+                            qui fournit des connexions JDBC à Hibernate
+                            <para>
+                                <emphasis role="strong">ex.</emphasis> 
+                                <literal>classname.of.ConnectionProvider</literal>
+                            </para>
+                        </entry>
+                    </row>
+                    <row>
+                    <entry>
+                        <literal>hibernate.connection.isolation</literal>
+                    </entry>
+                    <entry>
+                        Définit le niveau d'isolation des transactions JDBC. Regardez
+                        <literal>java.sql.Connection</literal> pour connaître le
+                        sens des différentes valeurs mais notez également que la plupart
+                        des bases de données ne supportent pas tous les niveaux d'isolation.
+                        <para>
+                            <emphasis role="strong">ex.</emphasis> 
+                            <literal>1, 2, 4, 8</literal>
+                        </para>
+                    </entry>
+                    </row>
+                    <row>
+                        <entry>
+                            <literal>hibernate.connection.autocommit</literal>
+                        </entry>
+                        <entry>
+                            Active le mode de commit automatique (autocommit) pour les connexions
+                            JDBC du pool (non recommandé).
+                            <para>
+                                <emphasis role="strong">ex.</emphasis>
+                                <literal>true</literal> | <literal>false</literal>
+                            </para>
+                        </entry>
+                    </row>
+                    <row>
+                        <entry>
+                            <literal>hibernate.connection.release_mode</literal>
+                        </entry>
+                        <entry>
+                            Spécifie à quel moment Hibernate doit relacher les connexion JDBC.
+                            Par défaut une connexion JDBC est conservée jusqu'à ce que la session
+                            soit explicitement fermée ou déconnectée. Pour une source de données
+                            JTA d'un serveur d'application, vous devriez utiliser <literal>after_statement</literal>
+                            pour libérer les connexions de manière plus agressive après chaque appel
+                            JDBC. Pour une connexion non JTA, il est souvent préférable de libérer
+                            la connexion à la fin de chaque transaction en utilisant <literal>after_transaction</literal>.
+                            <literal>auto</literal> choisira <literal>after_statement</literal> pour
+                            des transactions JTA et CMT et <literal>after_transaction</literal> pour
+                            des transactions JDBC.
+                            <para>
+                                <emphasis role="strong">ex.</emphasis> 
+                                <literal>on_close</literal> (default) | <literal>after_transaction</literal> |
+                                <literal>after_statement</literal> | <literal>auto</literal>
+                            </para>
+                        </entry>
+                    </row>
+                    <row>
+                    <entry>
+                        <literal>hibernate.connection.<emphasis>&lt;propertyName&gt;</emphasis></literal>
+                    </entry>
+                    <entry>
+                        Passe la propriété JDBC<literal>propertyName</literal>
+                        à <literal>DriverManager.getConnection()</literal>.
+                    </entry>
+                    </row>
+                    <row>
+                        <entry>
+                            <literal>hibernate.jndi.<emphasis>&lt;propertyName&gt;</emphasis></literal>
+                        </entry>
+                        <entry>
+                           Passe la propriété <literal>propertyName</literal> à l'<literal>InitialContextFactory</literal>
+                           de JNDI.
+                        </entry>
+                    </row>
+                </tbody>
+            </tgroup>
+        </table>
+
+        <table frame="topbot" id="configuration-cache-properties" revision="7">
+            <title>Propriétés du Cache d'Hibernate</title>
+            <tgroup cols="2">
+                <colspec colname="c1" colwidth="1*"/>
+                <colspec colname="c2" colwidth="1*"/>
+                <thead>
+                    <row>
+                        <entry>Nom de la propriété</entry>
+                        <entry>Fonction</entry>
+                    </row>
+                </thead>
+                <tbody>
+                    <row>
+                        <entry>
+                            <literal>hibernate.cache.provider_class</literal>
+                        </entry>
+                        <entry>
+                            Le nom de classe d'un <literal>CacheProvider</literal> 
+                            spécifique.
+                            <para>
+                                <emphasis role="strong">ex.</emphasis> 
+                                <literal>nom.de.classe.du.CacheProvider</literal>
+                            </para>
+                        </entry>
+                    </row>
+                    <row>
+                        <entry>
+                            <literal>hibernate.cache.use_minimal_puts</literal>
+                        </entry>
+                        <entry>
+                            Optimise le cache de second niveau en minimisant les écritures,
+                            au prix de plus de lectures. Ce paramètre est surtout utile pour
+                            les caches en cluster et est activé par défaut dans hibernate3
+                            pour les implémentations de cache en cluster.
+                            <para>
+                                <emphasis role="strong">ex.</emphasis> 
+                                <literal>true|false</literal>
+                            </para>
+                        </entry>
+                    </row>
+                    <row>
+                        <entry>
+                            <literal>hibernate.cache.use_query_cache</literal>
+                        </entry>
+                        <entry>
+                            Activer le cache de requête, les requêtes individuelles doivent tout
+                            de même être déclarées comme pouvant être mise en cache.
+                            <para>
+                                <emphasis role="strong">ex.</emphasis> 
+                                <literal>true|false</literal>
+                            </para>
+                        </entry>
+                    </row>
+                    <row>
+                        <entry>
+                            <literal>hibernate.cache.use_second_level_cache</literal>
+                        </entry>
+                        <entry>
+                            Peut être utilisé pour désactiver complètement le cache de second niveau
+                            qui est activé par défaut pour les classes qui spécifient un élément
+                            <literal>&lt;cache&gt;</literal> dans leur mapping.
+                            <para>
+                                <emphasis role="strong">ex.</emphasis> 
+                                <literal>true|false</literal>
+                            </para>
+                        </entry>
+                    </row>
+                    <row>
+                        <entry>
+                            <literal>hibernate.cache.query_cache_factory</literal>
+                        </entry>
+                        <entry>
+                            Le nom de classe d'une interface <literal>QueryCacheFactory</literal> ,
+                            par défaut = built-in <literal>StandardQueryCacheFactory</literal>.
+                            <para>
+                                <emphasis role="strong">ex.</emphasis>
+                                <literal>nom.de.la.classe.de.QueryCacheFactory</literal>
+                            </para>
+                        </entry>
+                    </row>
+
+                    <row>
+                        <entry>
+                            <literal>hibernate.cache.region_prefix</literal>
+                        </entry>
+                        <entry>
+                            Un préfixe à utiliser pour le nom des régions du 
+                            cache de second niveau.
+                            <para>
+                                <emphasis role="strong">ex.</emphasis> 
+                                <literal>prefix</literal>
+                            </para>
+                        </entry>
+                    </row>
+                    <row>
+                        <entry>
+                            <literal>hibernate.cache.use_structured_entries</literal>
+                        </entry>
+                        <entry>
+                            Force Hibernate à stocker les données dans le cache de
+                            second niveau dans un format plus adapté à la visualisation
+                            par un humain.
+                            <para>
+                                <emphasis role="strong">ex.</emphasis>
+                                <literal>true|false</literal>
+                            </para>
+                        </entry>
+                    </row>
+                </tbody>
+            </tgroup>
+        </table>
+
+        <table frame="topbot" id="configuration-transaction-properties" revision="9">
+            <title>Propriétés des transactions Hibernate</title>
+            <tgroup cols="2">
+                <colspec colname="c1" colwidth="1*"/>
+                <colspec colname="c2" colwidth="1*"/>
+                <thead>
+                    <row>
+                        <entry>Nom de la propriété</entry>
+                        <entry>Fonction</entry>
+                    </row>
+                </thead>
+                <tbody>
+                    <row>
+                        <entry>
+                            <literal>hibernate.transaction.factory_class</literal>
+                        </entry>
+                        <entry>
+                            Le nom de classe d'une <literal>TransactionFactory</literal>
+                            qui sera utilisée par l'API <literal>Transaction</literal>
+                            d'Hibernate (la valeur par défaut est 
+                            <literal>JDBCTransactionFactory</literal>).
+                            <para>
+                                <emphasis role="strong">ex.</emphasis> 
+                                <literal>nom.de.classe.d.une.TransactionFactory</literal>
+                            </para>
+                        </entry>
+                    </row>
+                    <row>
+                        <entry>
+                            <literal>jta.UserTransaction</literal>
+                        </entry>
+                        <entry>
+                            Le nom JNDI utilisé par la <literal>JTATransactionFactory</literal>
+                            pour obtenir la <literal>UserTransaction</literal> JTA du serveur 
+                            d'applications.
+                            <para>
+                                <emphasis role="strong">eg.</emphasis> 
+                                <literal>jndi/nom/compose</literal>
+                            </para>
+                        </entry>
+                    </row>
+                    <row>
+                        <entry>
+                            <literal>hibernate.transaction.manager_lookup_class</literal>
+                        </entry>
+                        <entry>
+                            Le nom de la classe du <literal>TransactionManagerLookup</literal>
+                            - requis lorsque le cache de niveau JVM est activé ou lorsque l'on
+                            utilise un générateur hilo dans un environnement JTA.
+                            <para>
+                                <emphasis role="strong">ex.</emphasis> 
+                                <literal>nom.de.classe.du.TransactionManagerLookup</literal>
+                            </para>
+                        </entry>
+                    </row>
+                    <row>
+                        <entry>
+                            <literal>hibernate.transaction.flush_before_completion</literal>
+                        </entry>
+                        <entry>
+                            Si activé, la session sera automatiquement vidée durant la phase
+                            qui précède la fin de la transaction (before completion). 
+                            La gestion automatique de contexte fourni par Hibernate est
+                            recommandée, voir
+                            <xref linkend="architecture-current-session"/>.
+                            <para>
+                                <emphasis role="strong">ex.</emphasis> 
+                                <literal>true</literal> | <literal>false</literal>
+                            </para>
+                        </entry>
+                    </row>
+                    <row>
+                        <entry>
+                            <literal>hibernate.transaction.auto_close_session</literal>
+                        </entry>
+                        <entry>
+                            Si activé, la session sera automatiquement fermé pendant la phase 
+                            qui suit la fin de la transaction (after completion). 
+                            La gestion automatique de contexte fourni par Hibernate est
+                            recommandée, voir
+                            <para>
+                                <emphasis role="strong">ex.</emphasis> 
+                                <literal>true</literal> | <literal>false</literal>
+                            </para>
+                        </entry>
+                    </row>
+                </tbody>
+            </tgroup>
+        </table>
+
+        <table frame="topbot" id="configuration-misc-properties" revision="9">
+            <title>Propriétés diverses</title>
+            <tgroup cols="2">
+                <colspec colname="c1" colwidth="1*"/>
+                <colspec colname="c2" colwidth="1*"/>
+                <thead>
+                    <row>
+                        <entry>Nom de la propriété</entry>
+                        <entry>Fonction</entry>
+                    </row>
+                </thead>
+                <tbody>
+                     <row>
+                        <entry>
+                            <literal>hibernate.current_session_context_class</literal>
+                        </entry>
+                        <entry>
+                            Fournit une stratégie particulière pour contextualiser
+                            la <literal>Session</literal> courante. Voir
+                            <xref linkend="architecture-current-session"/> pour plus
+                            d'informations sur les stratégies fournies.
+                            <para>
+                                <emphasis role="strong">eg.</emphasis>
+                                <literal>jta</literal> | <literal>thread</literal> |
+                                <literal>custom.Class</literal>
+                            </para>
+                        </entry>
+                    </row>
+                    <row>
+                        <entry>
+                            <literal>hibernate.query.factory_class</literal>
+                        </entry>
+                        <entry>
+                            Choisi l'implémentation du parseur de requête
+                            <para>
+                                <emphasis role="strong">ex.</emphasis> 
+                                <literal>org.hibernate.hql.ast.ASTQueryTranslatorFactory</literal> ou
+                                <literal>org.hibernate.hql.classic.ClassicQueryTranslatorFactory</literal>
+                            </para>
+                        </entry>
+                    </row>
+                    <row>
+                        <entry>
+                            <literal>hibernate.query.substitutions</literal>
+                        </entry>
+                        <entry>
+                            Lien entre les tokens de requêtes Hibernate et les 
+                            tokens SQL (les tokens peuvent être des fonctions ou des
+                            noms littéraux par exemple).
+                            <para>
+                                <emphasis role="strong">ex.</emphasis> 
+                                <literal>hqlLiteral=SQL_LITERAL, hqlFunction=SQLFUNC</literal>
+                            </para>
+                        </entry>
+                    </row>
+                    <row>
+                        <entry>
+                            <literal>hibernate.hbm2ddl.auto</literal>
+                        </entry>
+                        <entry>
+                            Valide ou exporte  automatiquement le schéma DDL vers la base de données
+                            lorsque la <literal>SessionFactory</literal> est créée.
+                            La valeur <literal>create-drop</literal> permet de supprimer 
+                            le schéma de base de données lorsque la <literal>SessionFactory</literal>
+                            est fermée explicitement.
+                            <para>
+                                <emphasis role="strong">ex.</emphasis> 
+                                <literal>validate</literal> | <literal>update</literal> | 
+                                <literal>create</literal> | <literal>create-drop</literal>
+                            </para>
+                        </entry>
+                    </row>
+                    <row>
+                        <entry>
+                            <literal>hibernate.cglib.use_reflection_optimizer</literal>
+                        </entry>
+                        <entry>
+                            Active l'utilisation de CGLIB à la place de la réflexion à l'exécution
+                            (Propriété de niveau système). La réflexion peut parfois être utile pour
+                            résoudre des problèmes. Notez qu'Hibernate a tout de même toujours besoin
+                            de CGLIB même si l'optimiseur est désactivé. Cette optimisation ne peut être
+                            définie que dans le fichier <literal>hibernate.cfg.xml</literal>.
+                            <para>
+                                <emphasis role="strong">ex.</emphasis> 
+                                <literal>true</literal> | <literal>false</literal>
+                            </para>
+                        </entry>
+                    </row>
+                </tbody>
+            </tgroup>
+        </table>
+
+        <sect2 id="configuration-optional-dialects" revision="1">
+            <title>Dialectes SQL</title>
+
+            <para>
+                Vous devriez toujours positionner la propriété <literal>hibernate.dialect</literal> à
+                la sous-classe de <literal>org.hibernate.dialect.Dialect</literal> appropriée à 
+                votre base de données. Si vous spécifiez un dialecte,
+                Hibernate utilisera des valeurs adaptées pour certaines autres
+                propriétés listées ci-dessus, vous évitant l'effort de le faire à la main.
+            </para>
+
+            <table frame="topbot" id="sql-dialects" revision="2">
+                <title>Dialectes SQL d'Hibernate (<literal>hibernate.dialect</literal>)</title>
+                <tgroup cols="2">
+                    <colspec colwidth="1*"/>
+                    <colspec colwidth="2.5*"/>
+                    <thead>
+                        <row>
+                            <entry>SGBD</entry>
+                            <entry>Dialecte</entry>
+                        </row>
+                    </thead>
+                    <tbody>
+                        <row>
+                            <entry>DB2</entry> <entry><literal>org.hibernate.dialect.DB2Dialect</literal></entry>
+                        </row>
+                        <row>
+                            <entry>DB2 AS/400</entry> <entry><literal>org.hibernate.dialect.DB2400Dialect</literal></entry>
+                        </row>
+                        <row>
+                            <entry>DB2 OS390</entry> <entry><literal>org.hibernate.dialect.DB2390Dialect</literal></entry>
+                        </row>
+                        <row>
+                            <entry>PostgreSQL</entry> <entry><literal>org.hibernate.dialect.PostgreSQLDialect</literal></entry>
+                        </row>
+                        <row>
+                            <entry>MySQL</entry> <entry><literal>org.hibernate.dialect.MySQLDialect</literal></entry>
+                        </row>
+                        <row>
+                            <entry>MySQL with InnoDB</entry> <entry><literal>org.hibernate.dialect.MySQLInnoDBDialect</literal></entry>
+                        </row>
+                        <row>
+                            <entry>MySQL with MyISAM</entry> <entry><literal>org.hibernate.dialect.MySQLMyISAMDialect</literal></entry>
+                        </row>
+                        <row>
+                            <entry>Oracle (any version)</entry> <entry><literal>org.hibernate.dialect.OracleDialect</literal></entry>
+                        </row>
+                        <row>
+                            <entry>Oracle 9i/10g</entry> <entry><literal>org.hibernate.dialect.Oracle9Dialect</literal></entry>
+                        </row>
+                        <row>
+                            <entry>Sybase</entry> <entry><literal>org.hibernate.dialect.SybaseDialect</literal></entry>
+                        </row>
+                        <row>
+                            <entry>Sybase Anywhere</entry> <entry><literal>org.hibernate.dialect.SybaseAnywhereDialect</literal></entry>
+                        </row>
+                        <row>
+                            <entry>Microsoft SQL Server</entry> <entry><literal>org.hibernate.dialect.SQLServerDialect</literal></entry>
+                        </row>
+                        <row>
+                            <entry>SAP DB</entry> <entry><literal>org.hibernate.dialect.SAPDBDialect</literal></entry>
+                        </row>
+                        <row>
+                            <entry>Informix</entry> <entry><literal>org.hibernate.dialect.InformixDialect</literal></entry>
+                        </row>
+                        <row>
+                            <entry>HypersonicSQL</entry> <entry><literal>org.hibernate.dialect.HSQLDialect</literal></entry>
+                        </row>
+                        <row>
+                            <entry>Ingres</entry> <entry><literal>org.hibernate.dialect.IngresDialect</literal></entry>
+                        </row>
+                        <row>
+                            <entry>Progress</entry> <entry><literal>org.hibernate.dialect.ProgressDialect</literal></entry>
+                        </row>
+                        <row>
+                            <entry>Mckoi SQL</entry> <entry><literal>org.hibernate.dialect.MckoiDialect</literal></entry>
+                        </row>
+                        <row>
+                            <entry>Interbase</entry> <entry><literal>org.hibernate.dialect.InterbaseDialect</literal></entry>
+                        </row>
+                        <row>
+                            <entry>Pointbase</entry> <entry><literal>org.hibernate.dialect.PointbaseDialect</literal></entry>
+                        </row>
+                        <row>
+                            <entry>FrontBase</entry> <entry><literal>org.hibernate.dialect.FrontbaseDialect</literal></entry>
+                        </row>
+                        <row>
+                            <entry>Firebird</entry> <entry><literal>org.hibernate.dialect.FirebirdDialect</literal></entry>
+                        </row>
+                    </tbody>
+                </tgroup>
+            </table>
+
+        </sect2>
+
+        <sect2 id="configuration-optional-outerjoin" revision="4">
+            <title>Chargement par Jointure Ouverte</title>
+
+            <para>
+                Si votre base de données supporte les outer joins de type ANSI, Oracle ou Sybase, 
+                <emphasis>le chargement par jointure ouverte</emphasis> devrait améliorer les 
+                performances en limitant le nombre d'aller-retour avec la base de données (la
+                base de données effectuant donc potentiellement plus de travail). Le chargement par
+                jointure ouverte permet à un graphe entier d'objets connectés par une relation plusieurs-à-un,
+                un-à-plusieurs ou un-à-un d'être chargé en un seul <literal>SELECT</literal> SQL.
+            </para>
+
+            <para>
+                Le chargement par jointure ouverte peut être désactiver <emphasis>globalement</emphasis>
+                en mettant la propriété <literal>hibernate.max_fetch_depth</literal> à <literal>0</literal>.
+                Une valeur de <literal>1</literal> ou plus active le chargement par jointure ouverte
+                pour les associatiosn un-à-un et plusieurs-à-un qui ont été mappée avec
+                <literal>fetch="join"</literal>.
+            </para>
+
+            <para>
+                Reportez vous à <xref linkend="performance-fetching"/> pour plus d'information.
+            </para>
+
+        </sect2>
+
+        <sect2 id="configuration-optional-binarystreams" revision="1">
+            <title>Flux binaires</title>
+
+            <para>
+                Oracle limite la taille d'un tableau de <literal>byte</literal> qui peuvent être
+                passées à et vers son pilote JDBC. Si vous souhaitez utiliser des instances larges
+                de type <literal>binary</literal> ou <literal>serializable</literal>, vous devez activer
+                la propriété <literal>hibernate.jdbc.use_streams_for_binary</literal>. <emphasis>C'est une 
+                fonctionalité de niveau système uniquement.</emphasis>
+            </para>
+
+        </sect2>
+
+        <sect2 id="configuration-optional-cacheprovider" revision="2">
+            <title>Cache de second niveau et cache de requêtes</title>
+
+            <para>
+                Les propriétés préfixées par <literal>hibernate.cache</literal>
+                vous permettent d'utiliser un système de cache de second niveau. Ce cache
+                peut avoir une portée dans le processus ou même être utilisable dans un
+                système distribué. Référez vous au chapitre <xref linkend="performance-cache"/> 
+                pour plus de détails.
+            </para>
+
+        </sect2>
+        
+        <sect2 id="configuration-optional-querysubstitution">
+            <title>Substitution dans le langage de requêtage</title>
+
+            <para>
+                Vous pouvez définir de nouveaux tokens dans les requêtes Hibernate en utilisant la propriété
+                <literal>hibernate.query.substitutions</literal>. Par exemple :
+            </para>
+
+            <programlisting>hibernate.query.substitutions vrai=1, faux=0</programlisting>
+
+            <para>
+                remplacerait les tokens <literal>vrai</literal> et <literal>faux</literal> par
+                des entiers dans le SQL généré.
+            </para>
+
+            <programlisting>hibernate.query.substitutions toLowercase=LOWER</programlisting>
+
+            <para>
+                permettrait de renommer la fonction SQL <literal>LOWER</literal> en <literal>toLowercase</literal>
+            </para>
+
+        </sect2>
+
+        <sect2 id="configuration-optional-statistics" revision="2">
+            <title>Statistiques Hibernate</title>
+
+            <para>
+                Si vous activez <literal>hibernate.generate_statistics</literal>, Hibernate va
+                fournir un certains nombre de métriques utiles pour régler les performances
+                d'une application qui tourne via <literal>SessionFactory.getStatistics()</literal>.
+                Hibernate peut aussi être configuré pour exposer ces statistiques via JMX.
+                Lisez les Javadoc des interfaces dans le package
+                <literal>org.hibernate.stats</literal> pour plus d'informations.
+            </para>
+
+        </sect2>
+    </sect1>
+
+    <sect1 id="configuration-logging">
+        <title>Tracer</title>
+
+        <para>
+            Hibernate trace divers évènements en utilisant Apache commons-logging.
+        </para>
+
+        <para>
+            Le service commons-logging délèguera directement à Apache Log4j
+            (si vous incluez <literal>log4j.jar</literal> dans votre classpath)
+            ou le système de trace du JDK 1.4 (si vous tournez sous le JDK 1.4
+            et supérieur). Vous pouvez télécharger Log4j à partir de
+            <literal>http://jakarta.apache.org</literal>. Pour utiliser Log4j,
+            vous devrez placer dans votre classpath un fichier 
+            <literal>log4j.properties</literal>. Un exemple de fichier est distribué
+            avec Hibernate dans le répertoire <literal>src/</literal>.
+        </para>
+        
+        <para>
+            Nous vous recommandons fortement de vous familiariser avec les messages des traces 
+            d'Hibernate. Beaucoup de soins a été apporté pour donner le plus de détails
+            possible sans les rendre illisibles. C'est un outil essentiel en cas de soucis.
+            Les catégories de trace les plus intéressantes sont les suivantes :
+        </para>
+        
+            <table frame="topbot" id="log-categories" revision="2">
+                <title>Catégories de trace d'Hibernate</title>
+                <tgroup cols="2">
+                    <colspec colwidth="1*"/>
+                    <colspec colwidth="2.5*"/>
+                    <thead>
+                        <row>
+                            <entry>Catégorie</entry>
+                            <entry>Fonction</entry>
+                        </row>
+                    </thead>
+                    <tbody>
+                        <row>
+                            <entry><literal>org.hibernate.SQL</literal></entry>
+                            <entry>Trace toutes les requêts SQL de type DML (gestion des données) qui sont exécutées</entry>
+                        </row>
+                        <row>
+                            <entry><literal>org.hibernate.type</literal></entry>
+                            <entry>Trace tous les paramètres JDBC</entry>
+                        </row>
+                        <row>
+                            <entry><literal>org.hibernate.tool.hbm2ddl</literal></entry>
+                            <entry>Trace toutes les requêts SQL de type DDL (gestion de la structure de la base) qui sont exécutées</entry>
+                        </row>
+                        <row>
+                            <entry><literal>org.hibernate.pretty</literal></entry>
+                            <entry>
+                                Trace l'état de toutes les entités (20 entités maximum) qui
+                                sont associées avec la session hibernate au moment du flush
+                            </entry>
+                        </row>
+                        <row>
+                            <entry><literal>org.hibernate.cache</literal></entry>
+                            <entry>Trace toute l'activité du cache de second niveau</entry>
+                        </row>
+                        <row>
+                            <entry><literal>org.hibernate.transaction</literal></entry>
+                            <entry>Trace toute l'activité relative aux transactions</entry>
+                        </row>
+                        <row>
+                            <entry><literal>org.hibernate.jdbc</literal></entry>
+                            <entry>Trace toute acquisition de ressource JDBC</entry>
+                        </row>
+                        <row>
+                            <entry><literal>org.hibernate.hql.ast.AST</literal></entry>
+                            <entry>
+                                Trace l'arbre syntaxique des requêtes HQL et SQL durant l'analyse syntaxique des requêtes
+                            </entry>
+                        </row>
+                        <row>
+                            <entry><literal>org.hibernate.secure</literal></entry>
+                            <entry>Trace toutes les demandes d'autorisation JAAS</entry>
+                        </row>
+                        <row>
+                            <entry><literal>org.hibernate</literal></entry>
+                            <entry>
+                                Trace tout (beaucoupe d'informations, mais très utile pour résoudre les problèmes).
+                            </entry>
+                        </row>
+                    </tbody>
+                </tgroup>
+            </table>
+            
+        <para>
+            Lorsque vous développez des applications avec Hibernate, vous devriez quasiment toujours
+            travailler avec le niveau <literal>debug</literal> activé pour la catégorie
+            <literal>org.hibernate.SQL</literal>, ou sinon avec la propriété 
+            <literal>hibernate.show_sql</literal> activée.
+        </para>
+                       
+        
+    </sect1>
+
+    <sect1 id="configuration-namingstrategy">
+        <title>Implémenter une <literal>NamingStrategy</literal></title>
+
+        <para>
+            L'interface <literal>org.hibernate.cfg.NamingStrategy</literal> vous permet de
+            spécifier une "stratégie de nommage" des objets et éléments de la base de données.
+        </para>
+
+        <para>
+            Vous pouvez fournir des règles pour automatiquement générer les identifiants
+            de base de données à partir des identifiants Java, ou transformer une colonne
+            ou table "logique" donnée dans le fichier de mapping en une colonne ou table
+            "physique". Cette fonctionnalité aide à réduire la verbosité de documents
+            de mapping, en éliminant le bruit répétitif (les préfixes <literal>TBL_</literal>
+            par exemple). La stratégie par défaut utilisée par Hibernate est minimale.
+        </para>
+
+        <para>
+            Vous pouvez définir une stratégie différente en appelant
+            <literal>Configuration.setNamingStrategy()</literal> avant d'ajouter des
+            mappings :
+        </para>
+
+        <programlisting><![CDATA[SessionFactory sf = new Configuration()
+    .setNamingStrategy(ImprovedNamingStrategy.INSTANCE)
+    .addFile("Item.hbm.xml")
+    .addFile("Bid.hbm.xml")
+    .buildSessionFactory();]]></programlisting>
+    
+        <para>
+            <literal>net.sf.hibernate.cfg.ImprovedNamingStrategy</literal> est une 
+            stratégie fournie qui peut être utile comme point de départ de quelques
+            applications.
+        </para>
+
+    </sect1>
+
+    <sect1 id="configuration-xmlconfig" revision="2">
+        <title>Fichier de configuration XML</title>
+
+        <para>
+            Une approche alternative est de spécifier toute la configuration dans un
+            fichier nommé <literal>hibernate.cfg.xml</literal>. Ce fichier peut être 
+            utilisé à la place du fichier <literal>hibernate.properties</literal>, voire
+            même peut servir à surcharger les propriétés si les deux fichiers sont présents.
+        </para>
+
+        <para>
+            Le fichier de configuration XML doit par défaut se placer à la racine
+            du <literal>CLASSPATH</literal>. En voici un exemple :
+        </para>
+
+        <programlisting><![CDATA[<?xml version='1.0' encoding='utf-8'?>
+<!DOCTYPE hibernate-configuration PUBLIC
+    "-//Hibernate/Hibernate Configuration DTD//EN"
+    "http://hibernate.sourceforge.net/hibernate-configuration-3.0.dtd">
+
+<hibernate-configuration>
+
+    <!-- a SessionFactory instance listed as /jndi/name -->
+    <session-factory
+        name="java:hibernate/SessionFactory">
+
+        <!-- properties -->
+        <property name="connection.datasource">java:/comp/env/jdbc/MyDB</property>
+        <property name="dialect">org.hibernate.dialect.MySQLDialect</property>
+        <property name="show_sql">false</property>
+        <property name="transaction.factory_class">
+            org.hibernate.transaction.JTATransactionFactory
+        </property>
+        <property name="jta.UserTransaction">java:comp/UserTransaction</property>
+
+        <!-- mapping files -->
+        <mapping resource="org/hibernate/auction/Item.hbm.xml"/>
+        <mapping resource="org/hibernate/auction/Bid.hbm.xml"/>
+
+        <!-- cache settings -->
+        <class-cache class="org.hibernate.auction.Item" usage="read-write"/>
+        <class-cache class="org.hibernate.auction.Bid" usage="read-only"/>
+        <collection-cache collection="org.hibernate.auction.Item.bids" usage="read-write"/>
+
+    </session-factory>
+
+</hibernate-configuration>]]></programlisting>
+
+       <para>
+          Commme vous pouvez le voir, l'avantage de cette approche est l'externalisation
+          des noms des fichiers de mapping de la configuration. Le fichier <literal>hibernate.cfg.xml</literal>
+          est également plus pratique quand on commence à régler le cache d'Hibernate. Notez
+          que vous pouvez choisir entre utiliser <literal>hibernate.properties</literal> ou
+          <literal>hibernate.cfg.xml</literal>, les deux sont équivalents, sauf en ce qui
+          concerne les bénéfices de l'utilisation de la syntaxe XML mentionnés ci-dessus.
+       </para>
+ 
+       <para>
+           Avec la configuration XML, démarrer Hibernate devient donc aussi simple que ceci :
+       </para>
+
+       <programlisting><![CDATA[SessionFactory sf = new Configuration().configure().buildSessionFactory();]]></programlisting>
+
+
+
+    </sect1>
+
+    <sect1 id="configuration-j2ee" revision="1">
+        <title>Intégration à un serveur d'application J2EE</title>
+
+        <para>
+            Hibernate possède les points suivants d'intégration à l'infrastructure J2EE :
+        </para>
+
+        <itemizedlist>
+            <listitem>
+                <para>
+                <emphasis>Source de données gérée par le conteneur</emphasis> : Hibernate peut
+                utiliser des connexions JDBC gérées par le conteneur et fournie par l'intermédiaire
+                de JNDI. Souvent, un <literal>TransactionManager</literal> compatible JTA
+                et un <literal>ResourceManager</literal> s'occupent de la gestion des transactions (CMT).
+                Ils sont particulièrement prévus pour pouvoir gérer des transactions distribuées
+                sur plusieurs sources de données. Vous pouvez bien sûr également définir vos
+                limites de transaction dans votre programme (BMT) ou vous pouvez sinon aussi
+                utiliser l'API optionnelle <literal>Transaction</literal> d'Hibernate qui vous garantira
+                la portabilité de votre code entre plusieurs serveurs d'application.
+                </para>
+            </listitem>
+        </itemizedlist>
+
+        <itemizedlist>
+            <listitem>
+                <para>
+                <emphasis>Association JNDI automatique</emphasis>: Hibernate peut associer sa
+                <literal>SessionFactory</literal> à JNDI après le démarrage.
+                </para>
+            </listitem>
+        </itemizedlist>
+
+        <itemizedlist>
+            <listitem>
+                <para>
+                <emphasis>Association de la Session à JTA:</emphasis> La <literal>Session</literal> Hibernate
+                peut être associée automatiquement à une transaction JTA si vous utilisez les EJBs.
+                Vous avez juste à récupérer la <literal>SessionFactory</literal> depuis JNDI et
+                à récupérer la <literal>Session</literal> courante. Hibernate s'occupe de vider et
+                fermer la <literal>Session</literal> lorsque le transaction JTA se termine. La
+                démarcation des transactions se fait de manière déclarative dans les descripteurs de déploiement.
+                </para>
+            </listitem>
+        </itemizedlist>
+
+        <itemizedlist>
+            <listitem>
+                <para>
+                <emphasis>Déploiement JMX :</emphasis>Si vous avez un serveur d'application compatible JMX
+                (JBoss AS par exemple), vous pouvez choisir de déployer Hibernate en temps que MBean géré par
+                le serveur. Cela vous évite de coder la ligne de démarrage qui permet de construire
+                la <literal>SessionFactory</literal> depuis la <literal>Configuration</literal>.
+                Le conteneur va démarrer votre <literal>HibernateService</literal>, et va idéalement
+                s'occuper des dépendances entre les services (la source de données doit être disponible
+                avant qu'Hibernate ne démarre, etc).
+                </para>
+            </listitem>
+        </itemizedlist>
+
+        <para>
+            En fonction de votre environnement, vous devrez peut être mettre l'option de 
+            configuration <literal>hibernate.connection.aggressive_release</literal> à vrai si
+            le serveur d'application affiche des exceptions de type "connection containment".
+        </para>
+
+        <sect2 id="configuration-optional-transactionstrategy" revision="3">
+            <title>Configuration de la stratégie transactionnelle</title>
+
+            <para>
+                L'API de la <literal>Session</literal> Hibernate est indépendante de tout système
+                de démarcation des transactions qui peut être présent dans votre architecture. Si
+                vous laissez Hibernate utiliser l'API JDBC directement via un pool de connexion, vous
+                devrez commencer et terminer vos transactions en utilisant l'API JDBC. Si votre
+                application tourne à l'intérieur d'un serveur d'application J2EE, vous voudrez peut être
+                utiliser les transactions gérées par les beans (BMT) et appeller l'API JTA et 
+                <literal>UserTransaction</literal> lorsque cela est nécessaire.
+            </para>
+            <para>
+                Pour conserver votre code portable entre ces deux environnements (et d'autres éventuels)
+                nous vous recommandons d'utiliser l'API optionnelle <literal>Transaction</literal> d'Hibernate,
+                qui va encapsuler et masquer le système de transaction sous-jacent.
+                Pour cela, vous devez préciser une classe de fabrique d'instances de <literal>Transaction</literal>
+                en positionnant la propriété
+                <literal>hibernate.transaction.factory_class</literal>.
+            </para>
+
+            <para>
+                Il existe trois choix standards (fournis) :
+            </para>
+
+            <variablelist spacing="compact">
+                <varlistentry>
+                    <term><literal>net.sf.hibernate.transaction.JDBCTransactionFactory</literal></term>
+                    <listitem>
+                        <para>délègue aux transactions de la base de données (JDBC). Valeur par défaut.</para>
+                    </listitem>
+                </varlistentry>
+                <varlistentry>
+                    <term><literal>org.hibernate.transaction.JTATransactionFactory</literal></term>
+                    <listitem>
+                        <para>
+                            délègue à CMT si une transaction existante est sous ce contexte (ex: méthode
+                            d'un EJB session), sinon une nouvelle transaction est entamée et
+                            une transaction gérée par le bean est utilisée.
+                        </para>
+                    </listitem>
+                </varlistentry>
+                <varlistentry>
+                    <term><literal>org.hibernate.transaction.CMTTransactionFactory</literal></term>
+                    <listitem>
+                        <para>délègue à aux transactions JTA gérées par le conteneur</para>
+                    </listitem>
+                </varlistentry>
+            </variablelist>
+
+            <para>
+                Vous pouvez également définir votre propre stratégie transactionnelle
+                (pour un service de transaction CORBA par exemple).
+            </para>
+
+            <para>
+                Certaines fonctionnalités d'Hibernate (i.e. le cache de second niveau, l'association
+                automatique des Session à JTA, etc.) nécessitent l'accès au <literal>TransactionManager</literal>
+                JTA dans un environnement "managé". Dans un serveur d'application, vous devez indiquer
+                comment Hibernate peut obtenir une référence vers le <literal>TransactionManager</literal>,
+                car J2EE ne fournit pas un seul mécanisme standard.
+            </para>
+
+            <table frame="topbot" id="jtamanagerlookup" revision="1">
+                <title>TransactionManagers JTA</title>
+                <tgroup cols="2">
+                    <colspec colwidth="2.5*"/>
+                    <colspec colwidth="1*"/>
+                    <thead>
+                        <row>
+                            <entry>Fabrique de Transaction</entry>
+                            <entry align="center">Serveur d'application</entry>
+                        </row>
+                    </thead>
+                    <tbody>
+                        <row>
+                            <entry><literal>org.hibernate.transaction.JBossTransactionManagerLookup</literal></entry>
+                            <entry align="center">JBoss</entry>
+                        </row>
+                        <row>
+                            <entry><literal>org.hibernate.transaction.WeblogicTransactionManagerLookup</literal></entry>
+                            <entry align="center">Weblogic</entry>
+                        </row>
+                        <row>
+                            <entry><literal>org.hibernate.transaction.WebSphereTransactionManagerLookup</literal></entry>
+                            <entry align="center">WebSphere</entry>
+                        </row>
+                        <row>
+                            <entry><literal>org.hibernate.transaction.WebSphereExtendedJTATransactionLookup</literal></entry>
+                            <entry align="center">WebSphere 6</entry>
+                        </row>
+                        <row>
+                            <entry><literal>org.hibernate.transaction.OrionTransactionManagerLookup</literal></entry>
+                            <entry align="center">Orion</entry>
+                        </row>
+                        <row>
+                            <entry><literal>org.hibernate.transaction.ResinTransactionManagerLookup</literal></entry>
+                            <entry align="center">Resin</entry>
+                        </row>
+                        <row>
+                            <entry><literal>org.hibernate.transaction.JOTMTransactionManagerLookup</literal></entry>
+                            <entry align="center">JOTM</entry>
+                        </row>
+                        <row>
+                            <entry><literal>org.hibernate.transaction.JOnASTransactionManagerLookup</literal></entry>
+                            <entry align="center">JOnAS</entry>
+                        </row>
+                        <row>
+                            <entry><literal>org.hibernate.transaction.JRun4TransactionManagerLookup</literal></entry>
+                            <entry align="center">JRun4</entry>
+                        </row>
+                        <row>
+                            <entry><literal>org.hibernate.transaction.BESTransactionManagerLookup</literal></entry>
+                            <entry align="center">Borland ES</entry>
+                        </row>
+                    </tbody>
+                </tgroup>
+            </table>
+
+        </sect2>
+
+        <sect2 id="configuration-optional-jndi" revision="3">
+            <title><literal>SessionFactory</literal> associée au JNDI</title>
+
+            <para>
+                Une <literal>SessionFactory</literal> Hibernate associée au JNDI peut 
+                simplifier l'accès à la fabrique et donc la création de nouvelles
+                <literal>Session</literal>s. Notez que cela n'est pas lié avec les <literal>Datasource</literal>
+                associées au JNDI, elles utilisent juste le même registre.
+            </para>
+
+            <para>
+                Si vous désirez associer la <literal>SessionFactory</literal> à un nom JNDI,
+                spécifiez un nom (ex. <literal>java:hibernate/SessionFactory</literal>) en
+                utilisant la propriété <literal>hibernate.session_factory_name</literal>.
+                Si cette propriété est omise, la <literal>SessionFactory</literal> ne sera pas
+                associée au JNDI (c'est particulièrement pratique dans les environnements ayant une
+                implémentation de JNDI en lecture seule, comme c'est le cas pour Tomcat).
+            </para>
+
+            <para>
+                Lorsqu'il associe la <literal>SessionFactory</literal> au JNDI, Hibernate utilisera 
+                les valeurs de <literal>hibernate.jndi.url</literal>, <literal>hibernate.jndi.class</literal>
+                pour instancier un contexte d'initialisation. S'ils ne sont pas spécifiés, 
+                l'<literal>InitialContext</literal> par défaut sera utilisé.
+            </para>
+            
+            <para>
+                Hibernate va automatiquement placer la <literal>SessionFactory</literal> dans JNDI
+                après avoir appelé <literal>cfg.buildSessionFactory()</literal>. Cela signifie que vous
+                devez avoir cet appel dans un code de démarrage (ou dans une classe utilitaire) dans
+                votre application sauf si vous utilisez le déploiement JMX avec le service
+                <literal>HibernateService</literal> présenté plus tard dans ce document.
+            </para>
+            <para>           
+                Si vous utilisez <literal>SessionFactory</literal> JNDI, un EJB ou n'importe quelle autre classe
+                peut obtenir la <literal>SessionFactory</literal> en utilisant un lookup JNDI.
+            </para>
+
+            <para>
+                Nous recommandons que vous liiez la <literal>SessionFactory</literal> à JNDI dans les
+                environnements managés et que vous utilisiez un singleton <literal>static</literal> si ce n'est pas le cas.
+                Pour isoler votre application de ces détails, nous vous recommandons aussi de masquer
+                le code de lookup actuel pour une <literal>SessionFactory</literal> dans une classe helper,
+                comme <literal>HibernateUtil.getSessionFactory()</literal>. Notez qu'une telle classe
+                est aussi un moyen efficace de démarrer Hibernate&mdash;voir chapitre 1.
+            </para>
+        </sect2>
+
+        <sect2 id="configuration-j2ee-currentsession" revision="4">
+            <title>Association automatique de la Session à JTA</title>
+
+            <para>
+                Le moyen le plus simple de gérer les <literal>Session</literal>s et transactions est
+                la gestion automatique de session "courante" offerte par Hibernate.
+                Voir détail à <xref linkend="architecture-current-session">current sessions</xref>.
+                En utilisant le contexte de session <literal>"jta"</literal> session context, s'il n'y a pas
+                de <literal>Session</literal> associée à la transaction JTA courante, une session sera
+                démarrée et associée à la transaction JTA courante la première fois que vous appelez
+                <literal>sessionFactory.getCurrentSession()</literal>. Les <literal>Session</literal>s
+                obtenue via <literal>getCurrentSession()</literal> dans une contexte <literal>"jta"</literal> 
+                seront automatiquement flushées avant la validation de la transaction, fermées une fois
+                la transaction complétée, et libéreront les connexions JDBC de manière aggressive
+                après chaque statement. Ceci permet aux <literal>Session</literal>s d'être
+                gérées par le cycle de vie de la transaction JTA à la quelle est sont associées, 
+                laissant le code de l'utilisateur propre de ce type de gestion. Votre code peut
+                soit utiliser JTA de manière programmatique via <literal>UserTransaction</literal>, ou (ce qui est recommandé
+                pour la portabilité du code) utiliser l'API <literal>Transaction</literal> API pour marquer
+                les limites. Si vous exécutez sous un conteneur EJB, la démarcation déclarative des transactions
+                avec CMT est recommandée.
+            </para>
+
+        </sect2>
+
+        <sect2 id="configuration-j2ee-jmx" revision="1">
+            <title>Déploiement JMX</title>
+
+            <para>
+                La ligne <literal>cfg.buildSessionFactory()</literal>  doit toujours être exécutée
+                quelque part pour avoir une <literal>SessionFactory</literal> dans JNDI. Vous pouvez
+                faire cela dans un bloc d'initialisation <literal>static</literal> (comme
+                celui qui se trouve dans la classe <literal>HibernateUtil</literal>) ou vous pouvez
+                déployer Hibernate en temps que <emphasis>service managé</emphasis>.
+            </para>
+
+            <para>
+                Hibernate est distribué avec <literal>org.hibernate.jmx.HibernateService</literal>
+                pour le déploiement sur un serveur d'application avec le support de JMX comme JBoss AS.
+                Le déploiement et la configuration sont spécifiques à chaque vendeur. Voici un fichier
+                <literal>jboss-service.xml</literal> d'exemple pour JBoss 4.0.x:
+            </para>
+
+            <programlisting><![CDATA[<?xml version="1.0"?>
+<server>
+
+<mbean code="org.hibernate.jmx.HibernateService"
+    name="jboss.jca:service=HibernateFactory,name=HibernateFactory">
+
+    <!-- Required services -->
+    <depends>jboss.jca:service=RARDeployer</depends>
+    <depends>jboss.jca:service=LocalTxCM,name=HsqlDS</depends>
+
+    <!-- Bind the Hibernate service to JNDI -->
+    <attribute name="JndiName">java:/hibernate/SessionFactory</attribute>
+
+    <!-- Datasource settings -->
+    <attribute name="Datasource">java:HsqlDS</attribute>
+    <attribute name="Dialect">org.hibernate.dialect.HSQLDialect</attribute>
+
+    <!-- Transaction integration -->
+    <attribute name="TransactionStrategy">
+        org.hibernate.transaction.JTATransactionFactory</attribute>
+    <attribute name="TransactionManagerLookupStrategy">
+        org.hibernate.transaction.JBossTransactionManagerLookup</attribute>
+    <attribute name="FlushBeforeCompletionEnabled">true</attribute>
+    <attribute name="AutoCloseSessionEnabled">true</attribute>
+
+    <!-- Fetching options -->
+    <attribute name="MaximumFetchDepth">5</attribute>
+
+    <!-- Second-level caching -->
+    <attribute name="SecondLevelCacheEnabled">true</attribute>
+    <attribute name="CacheProviderClass">org.hibernate.cache.EhCacheProvider</attribute>
+    <attribute name="QueryCacheEnabled">true</attribute>
+
+    <!-- Logging -->
+    <attribute name="ShowSqlEnabled">true</attribute>
+
+    <!-- Mapping files -->
+    <attribute name="MapResources">auction/Item.hbm.xml,auction/Category.hbm.xml</attribute>
+
+</mbean>
+
+</server>]]></programlisting>
+
+            <para>
+                Ce fichier est déployé dans un répertoire <literal>META-INF</literal> et est packagé
+                dans un fichier JAR avec l'extension <literal>.sar</literal> (service archive).
+                Vous devez également packager Hibernate, les librairies tierces requises, vos classes
+                persistantes compilées et vos fichiers de mapping dans la même archive. Vos beans
+                entreprise (souvent des EJBs session) peuvent rester dans leur propre fichier JAR mais
+                vous pouvez inclure ce fichier JAR dans le jar principal du service pour avoir une seule unité
+                déployable à chaud. Vous pouvez consulter la documentation de JBoss AS pour plus d'information
+                sur les services JMX et le déploiement des EJBs.
+            </para>
+
+        </sect2>
+
+
+    </sect1>
+
+
+
+
+</chapter>

Copied: core/trunk/documentation/manual/fr-FR/src/main/docbook/content/events.xml (from rev 14070, core/trunk/documentation/manual/fr-FR/src/main/docbook/modules/events.xml)
===================================================================
--- core/trunk/documentation/manual/fr-FR/src/main/docbook/content/events.xml	                        (rev 0)
+++ core/trunk/documentation/manual/fr-FR/src/main/docbook/content/events.xml	2007-10-09 18:28:36 UTC (rev 14074)
@@ -0,0 +1,263 @@
+<?xml version="1.0" encoding="iso-8859-1"?>
+<chapter id="events">
+    <title>Les intercepteurs et les événements</title>
+
+    <para>
+        Il est souvent utile pour l'application de réagir à certains événements
+        qui surviennent dans Hibernate. Cela autorise l'implémentation de certaines sortes de
+        fonctionnalités génériques, et d'extensions de fonctionnalités d'Hibernate.
+    </para>
+
+    <sect1 id="objectstate-interceptors" revision="2">
+        <title>Intercepteurs</title>
+
+        <para>
+            L'interface <literal>Interceptor</literal> fournit des "callbacks" de la session vers l'application 
+            et permettent à l'application de consulter et/ou de manipuler des propriétés
+            d'un objet persistant avant qu'il soit sauvegardé, mis à jour, supprimé ou chargé.
+            Une utilisation possible de cette fonctionnalité est de tracer l'accès à l'information.
+            Par exemple, l'<literal>Interceptor</literal> suivant positionne
+            <literal>createTimestamp</literal> quand un <literal>Auditable</literal> est créé
+            et met à jour la propriété <literal>lastUpdateTimestamp</literal> quand un
+            <literal>Auditable</literal> est mis à jour.
+        </para>
+
+        <para>
+            Vous pouvez soit implémenter <literal>Interceptor</literal> directement ou (mieux)
+            étendre <literal>EmptyInterceptor</literal>.
+        </para>
+
+        <programlisting><![CDATA[package org.hibernate.test;
+
+import java.io.Serializable;
+import java.util.Date;
+import java.util.Iterator;
+
+import org.hibernate.EmptyInterceptor;
+import org.hibernate.Transaction;
+import org.hibernate.type.Type;
+
+public class AuditInterceptor extends EmptyInterceptor {
+
+    private int updates;
+    private int creates;
+    private int loads;
+
+    public void onDelete(Object entity,
+                         Serializable id,
+                         Object[] state,
+                         String[] propertyNames,
+                         Type[] types) {
+        // ne fait rien
+    }
+
+    public boolean onFlushDirty(Object entity,
+                                Serializable id,
+                                Object[] currentState,
+                                Object[] previousState,
+                                String[] propertyNames,
+                                Type[] types) {
+
+        if ( entity instanceof Auditable ) {
+            updates++;
+            for ( int i=0; i < propertyNames.length; i++ ) {
+                if ( "lastUpdateTimestamp".equals( propertyNames[i] ) ) {
+                    currentState[i] = new Date();
+                    return true;
+                }
+            }
+        }
+        return false;
+    }
+
+    public boolean onLoad(Object entity,
+                          Serializable id,
+                          Object[] state,
+                          String[] propertyNames,
+                          Type[] types) {
+        if ( entity instanceof Auditable ) {
+            loads++;
+        }
+        return false;
+    }
+
+    public boolean onSave(Object entity,
+                          Serializable id,
+                          Object[] state,
+                          String[] propertyNames,
+                          Type[] types) {
+
+        if ( entity instanceof Auditable ) {
+            creates++;
+            for ( int i=0; i<propertyNames.length; i++ ) {
+                if ( "createTimestamp".equals( propertyNames[i] ) ) {
+                    state[i] = new Date();
+                    return true;
+                }
+            }
+        }
+        return false;
+    }
+
+    public void postFlush(Iterator entities) {
+        System.out.println("Creations: " + creates + ", Updates: " + updates);
+    }
+
+    public void afterTransactionCompletion(Transaction tx) {
+        if ( tx.wasCommitted() ) {
+            System.out.println("Creations: " + creates + ", Updates: " + updates, "Loads: " + loads);
+        }
+        updates=0;
+        creates=0;
+        loads=0;
+    }
+
+}]]></programlisting>
+
+        <para>
+            L'intercepteur doit être spécifié quand une session est créée.
+        </para>
+
+        <programlisting><![CDATA[Session session = sf.openSession( new AuditInterceptor() );]]></programlisting>
+
+        <para>
+            Vous pouvez aussi mettre un intercepteur au niveau global, en utilisant l'objet <literal>Configuration</literal>.
+            Dans ce cas, l'intercepteur doit être "threadsafe".
+        </para>
+
+        <programlisting><![CDATA[new Configuration().setInterceptor( new AuditInterceptor() );]]></programlisting>
+
+    </sect1>
+
+     <sect1 id="objectstate-events" revision="3">
+        <title>Système d'événements</title>
+
+        <para>
+            Si vous devez réagir à des événements particuliers dans votre couche de persistance,
+            vous pouvez aussi utiliser l'architecture d'<emphasis>événements</emphasis> d'Hibernate3.
+            Le système d'événements peut être utilisé en supplément ou en remplacement des interceptors.
+        </para>
+
+        <para>
+            Essentiellement toutes les méthodes de l'interface <literal>Session</literal> sont corrélées à
+            un événement. Vous avez un <literal>LoadEvent</literal>, un <literal>FlushEvent</literal>, etc
+            (consultez la DTD du fichier de configuration XML ou le paquet <literal>org.hibernate.event</literal>
+            pour avoir la liste complète des types d'événement définis).
+            Quand une requête est faite à partir d'une de ces méthodes, la
+            <literal>Session</literal> Hibernate génère un événement approprié et le passe
+            au listener configuré pour ce type.
+            Par défaut, ces listeners implémentent le même traitement dans lequel ces méthodes
+            aboutissent toujours.
+            Cependant, vous êtes libre d'implémenter une version personnalisée d'une de ces
+            interfaces de listener (c'est-à-dire, le <literal>LoadEvent</literal> est traité par
+            l'implémentation de l'interface <literal>LoadEventListener</literal> déclarée), dans
+            quel cas leur implémentation devrait être responsable du traitement des
+            requêtes <literal>load()</literal> faites par la <literal>Session</literal>.
+        </para>
+
+        <para>
+            Les listeners devraient effectivement être considérés comme des singletons ; dans le sens
+            où ils sont partagés entre des requêtes, et donc ne devraient pas sauvegarder des états
+            de variables d'instance.
+        </para>
+
+        <para>
+            Un listener personnalisé devrait implémenter l'interface appropriée pour l'événement
+            qu'il veut traiter et/ou étendre une des classes de base (ou même l'événement prêt à
+            l'emploi utilisé par Hibernate comme ceux déclarés non-finaux à cette intention). Les
+            listeners personnalisés peuvent être soit inscrits par programmation à travers l'objet
+            <literal>Configuration</literal>, ou spécifiés la configuration XML d'Hibernate
+            (la configuration déclarative à travers le fichier de propriétés n'est pas supportée).
+            Voici un exemple de listener personnalisé pour l'événement de chargement :
+        </para>
+
+        <programlisting><![CDATA[public class MyLoadListener implements LoadEventListener {
+    // C'est une simple méthode définie par l'interface LoadEventListener
+    public void onLoad(LoadEvent event, LoadEventListener.LoadType loadType)
+            throws HibernateException {
+        if ( !MySecurity.isAuthorized( event.getEntityClassName(), event.getEntityId() ) ) {
+            throw MySecurityException("Unauthorized access");
+        }
+    }
+}]]></programlisting>
+
+        <para>
+            Vous avez aussi besoin d'une entrée de configuration disant à Hibernate d'utiliser
+            ce listener en plus du listener par défaut :
+        </para>
+
+<programlisting><![CDATA[<hibernate-configuration>
+    <session-factory>
+        ...
+        <event type="load">
+            <listener class="com.eg.MyLoadListener"/>
+            <listener class="org.hibernate.event.def.DefaultLoadEventListener"/>
+        </event>
+    </session-factory>
+</hibernate-configuration>]]></programlisting>
+
+        <para>
+            Vous pouvez aussi l'inscrire par programmation :
+        </para>
+
+        <programlisting><![CDATA[Configuration cfg = new Configuration();
+LoadEventListener[] stack = { new MyLoadListener(), new DefaultLoadEventListener() };
+cfg.EventListeners().setLoadEventListeners(stack);]]></programlisting>
+
+        <para>
+            Les listeners inscrits déclarativement ne peuvent pas partager d'instances. Si le même
+            nom de classe est utilisée dans plusieurs éléments <literal>&lt;listener/&gt;</literal>,
+            chaque référence sera une instance distincte de cette classe. Si vous avez besoin de la
+            faculté de partager des instances de listener entre plusieurs types de listener, vous devez
+            utiliser l'approche d'inscription par programmation.
+        </para>
+
+        <para>
+            Pourquoi implémenter une interface et définir le type spécifique durant la configuration ?
+            Une implémentation de listener pourrait implémenter plusieurs interfaces de listener
+            d'événements. Avoir en plus le type défini durant l'inscription rend plus facile
+            l'activation ou la désactivation pendant la configuration.
+        </para>
+
+    </sect1>
+
+    <sect1 id="objectstate-decl-security" revision="2">
+        <title>Sécurité déclarative d'Hibernate</title>
+        <para>
+            Généralement, la sécurité déclarative dans les applications Hibernate est gérée dans la
+            couche de session. Maintenant, Hibernate3 permet à certaines actions d'être approuvées
+            via JACC, et autorisées via JAAS. Cette fonctionnalité optionnelle est construite
+            au dessus de l'architecture d'événements.
+        </para>
+
+        <para>
+            D'abord, vous devez configurer les listeners d'événements appropriés pour permettre
+            l'utilisation d'autorisations JAAS.
+        </para>
+
+        <programlisting><![CDATA[<listener type="pre-delete" class="org.hibernate.secure.JACCPreDeleteEventListener"/>
+<listener type="pre-update" class="org.hibernate.secure.JACCPreUpdateEventListener"/>
+<listener type="pre-insert" class="org.hibernate.secure.JACCPreInsertEventListener"/>
+<listener type="pre-load" class="org.hibernate.secure.JACCPreLoadEventListener"/>]]></programlisting>
+
+        <para>
+            Notez que <literal>&lt;listener type="..." class="..."/&gt;</literal> est juste un raccourci
+            pour <literal>&lt;event type="..."&gt;&lt;listener class="..."/&gt;&lt;/event&gt;</literal>
+            quand il y a exactement un listener pour un type d'événement particulier.
+        </para>
+
+        <para>
+            Ensuite, toujours dans <literal>hibernate.cfg.xml</literal>, lier les permissions aux rôles :
+        </para>
+
+        <programlisting><![CDATA[<grant role="admin" entity-name="User" actions="insert,update,read"/>
+<grant role="su" entity-name="User" actions="*"/>]]></programlisting>
+
+        <para>
+            Les noms de rôle sont les rôles compris par votre fournisseur JAAC.
+        </para>
+
+    </sect1>
+
+</chapter>
+

Copied: core/trunk/documentation/manual/fr-FR/src/main/docbook/content/example_mappings.xml (from rev 14070, core/trunk/documentation/manual/fr-FR/src/main/docbook/modules/example_mappings.xml)
===================================================================
--- core/trunk/documentation/manual/fr-FR/src/main/docbook/content/example_mappings.xml	                        (rev 0)
+++ core/trunk/documentation/manual/fr-FR/src/main/docbook/content/example_mappings.xml	2007-10-09 18:28:36 UTC (rev 14074)
@@ -0,0 +1,672 @@
+<?xml version="1.0" encoding="iso-8859-1"?>
+<!--
+  ~ Copyright (c) 2007, Red Hat Middleware, LLC. All rights reserved.
+  ~
+  ~ This copyrighted material is made available to anyone wishing to use, modify,
+  ~ copy, or redistribute it subject to the terms and conditions of the GNU
+  ~ Lesser General Public License, v. 2.1. This program is distributed in the
+  ~ hope that it will be useful, but WITHOUT A WARRANTY; without even the implied
+  ~ warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
+  ~ Lesser General Public License for more details. You should have received a
+  ~ copy of the GNU Lesser General Public License, v.2.1 along with this
+  ~ distribution; if not, write to the Free Software Foundation, Inc.,
+  ~ 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
+  ~
+  ~ Red Hat Author(s): Steve Ebersole
+  -->
+<chapter id="example-mappings">
+    <title>Exemple : quelques mappings</title>
+
+    <para>
+        Ce chapitre montre quelques mappings plus complexes.
+    </para>
+
+    <sect1 id="example-mappings-emp">
+        <title>Employeur/Employé (Employer/Employee)</title>
+
+        <para>
+            Le modèle suivant de relation entre <literal>Employer</literal> et
+            <literal>Employee</literal> utilise une vraie classe entité (<literal>Employment</literal>)
+            pour représenter l'association. On a fait cela parce qu'il peut y avoir plus d'une période
+            d'emploi pour les deux mêmes parties. Des composants sont utilisés pour modéliser les
+            valeurs monétaires et les noms des employés.
+        </para>
+
+        <mediaobject>
+            <imageobject role="fo">
+                <imagedata fileref="../images/EmployerEmployee.gif" format="GIF" align="center"/>
+            </imageobject>
+            <imageobject role="html">
+                <imagedata fileref="../images/EmployerEmployee.gif" format="GIF" align="center"/>
+            </imageobject>
+        </mediaobject>
+
+        <para>
+            Voici un document de mapping possible :
+        </para>
+
+        <programlisting><![CDATA[<hibernate-mapping>
+
+    <class name="Employer" table="employers">
+        <id name="id">
+            <generator class="sequence">
+                <param name="sequence">employer_id_seq</param>
+            </generator>
+        </id>
+        <property name="name"/>
+    </class>
+
+    <class name="Employment" table="employment_periods">
+
+        <id name="id">
+            <generator class="sequence">
+                <param name="sequence">employment_id_seq</param>
+            </generator>
+        </id>
+        <property name="startDate" column="start_date"/>
+        <property name="endDate" column="end_date"/>
+
+        <component name="hourlyRate" class="MonetaryAmount">
+            <property name="amount">
+                <column name="hourly_rate" sql-type="NUMERIC(12, 2)"/>
+            </property>
+            <property name="currency" length="12"/>
+        </component>
+
+        <many-to-one name="employer" column="employer_id" not-null="true"/>
+        <many-to-one name="employee" column="employee_id" not-null="true"/>
+
+    </class>
+
+    <class name="Employee" table="employees">
+        <id name="id">
+            <generator class="sequence">
+                <param name="sequence">employee_id_seq</param>
+            </generator>
+        </id>
+        <property name="taxfileNumber"/>
+        <component name="name" class="Name">
+            <property name="firstName"/>
+            <property name="initial"/>
+            <property name="lastName"/>
+        </component>
+    </class>
+
+</hibernate-mapping>]]></programlisting>
+
+    <para>
+        Et voici le schéma des tables générées par <literal>SchemaExport</literal>.
+    </para>
+
+    <programlisting><![CDATA[create table employers (
+    id BIGINT not null,
+    name VARCHAR(255),
+    primary key (id)
+)
+
+create table employment_periods (
+    id BIGINT not null,
+    hourly_rate NUMERIC(12, 2),
+    currency VARCHAR(12),
+    employee_id BIGINT not null,
+    employer_id BIGINT not null,
+    end_date TIMESTAMP,
+    start_date TIMESTAMP,
+    primary key (id)
+)
+
+create table employees (
+    id BIGINT not null,
+    firstName VARCHAR(255),
+    initial CHAR(1),
+    lastName VARCHAR(255),
+    taxfileNumber VARCHAR(255),
+    primary key (id)
+)
+
+alter table employment_periods
+    add constraint employment_periodsFK0 foreign key (employer_id) references employers
+alter table employment_periods
+    add constraint employment_periodsFK1 foreign key (employee_id) references employees
+create sequence employee_id_seq
+create sequence employment_id_seq
+create sequence employer_id_seq]]></programlisting>
+
+    </sect1>
+
+    <sect1 id="example-mappings-authorwork">
+        <title>Auteur/Travail (Author/Work)</title>
+
+        <para>
+            Soit le modèle de la relation entre <literal>Work</literal>, <literal>Author</literal>
+            et <literal>Person</literal>. Nous représentons la relation entre <literal>Work</literal>
+            et <literal>Author</literal> comme une association plusieurs-vers-plusieurs. Nous avons choisi de
+            représenter la relation entre <literal>Author</literal> et <literal>Person</literal>
+            comme une association un-vers-un. Une autre possibilité aurait été que
+            <literal>Author</literal> hérite de <literal>Person</literal>.
+        </para>
+
+        <mediaobject>
+            <imageobject role="fo">
+                <imagedata fileref="../images/AuthorWork.gif" format="GIF" align="center"/>
+            </imageobject>
+            <imageobject role="html">
+                <imagedata fileref="../images/AuthorWork.gif" format="GIF" align="center"/>
+            </imageobject>
+        </mediaobject>
+
+        <para>
+            Le mapping suivant représente exactement ces relations :
+        </para>
+
+        <programlisting><![CDATA[<hibernate-mapping>
+
+    <class name="Work" table="works" discriminator-value="W">
+
+        <id name="id" column="id">
+            <generator class="native"/>
+        </id>
+        <discriminator column="type" type="character"/>
+
+        <property name="title"/>
+        <set name="authors" table="author_work">
+            <key column name="work_id"/>
+            <many-to-many class="Author" column name="author_id"/>
+        </set>
+
+        <subclass name="Book" discriminator-value="B">
+            <property name="text"/>
+        </subclass>
+
+        <subclass name="Song" discriminator-value="S">
+            <property name="tempo"/>
+            <property name="genre"/>
+        </subclass>
+
+    </class>
+
+    <class name="Author" table="authors">
+
+        <id name="id" column="id">
+            <!-- The Author must have the same identifier as the Person -->
+            <generator class="assigned"/>
+        </id>
+
+        <property name="alias"/>
+        <one-to-one name="person" constrained="true"/>
+
+        <set name="works" table="author_work" inverse="true">
+            <key column="author_id"/>
+            <many-to-many class="Work" column="work_id"/>
+        </set>
+
+    </class>
+
+    <class name="Person" table="persons">
+        <id name="id" column="id">
+            <generator class="native"/>
+        </id>
+        <property name="name"/>
+    </class>
+
+</hibernate-mapping>]]></programlisting>
+
+    <para>
+        Il y a quatre tables dans ce mapping. <literal>works</literal>,
+        <literal>authors</literal> et <literal>persons</literal> qui contiennent
+        respectivement les données de work, author et person.
+        <literal>author_work</literal> est une table d'association qui lie authors
+        à works. Voici le schéma de tables, généré par <literal>SchemaExport</literal>.
+    </para>
+
+    <programlisting><![CDATA[create table works (
+    id BIGINT not null generated by default as identity,
+    tempo FLOAT,
+    genre VARCHAR(255),
+    text INTEGER,
+    title VARCHAR(255),
+    type CHAR(1) not null,
+    primary key (id)
+)
+
+create table author_work (
+    author_id BIGINT not null,
+    work_id BIGINT not null,
+    primary key (work_id, author_id)
+)
+
+create table authors (
+    id BIGINT not null generated by default as identity,
+    alias VARCHAR(255),
+    primary key (id)
+)
+
+create table persons (
+    id BIGINT not null generated by default as identity,
+    name VARCHAR(255),
+    primary key (id)
+)
+
+alter table authors
+    add constraint authorsFK0 foreign key (id) references persons
+alter table author_work
+    add constraint author_workFK0 foreign key (author_id) references authors
+alter table author_work
+    add constraint author_workFK1 foreign key (work_id) references works]]></programlisting>
+
+    </sect1>
+
+    <sect1 id="example-mappings-customerorderproduct">
+        <title>Client/Commande/Produit (Customer/Order/Product)</title>
+
+        <para>
+            Imaginons maintenant le modèle de relation entre <literal>Customer</literal>,
+            <literal>Order</literal>, <literal>LineItem</literal> et <literal>Product</literal>.
+            Il y a une association un-vers-plusieurs entre <literal>Customer</literal> et
+            <literal>Order</literal>, mais comment devrions nous représenter <literal>Order</literal> /
+            <literal>LineItem</literal> / <literal>Product</literal>? J'ai choisi de mapper
+            <literal>LineItem</literal> comme une classe d'association représentant l'association
+            plusieurs-vers-plusieurs entre <literal>Order</literal> et <literal>Product</literal>. Dans
+            Hibernate, on appelle cela un élément composite.
+        </para>
+
+        <mediaobject>
+            <imageobject role="fo">
+                <imagedata fileref="../images/CustomerOrderProduct.gif" format="GIF" align="center"/>
+            </imageobject>
+            <imageobject role="html">
+                <imagedata fileref="../images/CustomerOrderProduct.gif" format="GIF" align="center"/>
+            </imageobject>
+        </mediaobject>
+
+        <para>
+            Le document de mapping :
+        </para>
+
+        <programlisting><![CDATA[<hibernate-mapping>
+
+    <class name="Customer" table="customers">
+        <id name="id">
+            <generator class="native"/>
+        </id>
+        <property name="name"/>
+        <set name="orders" inverse="true">
+            <key column="customer_id"/>
+            <one-to-many class="Order"/>
+        </set>
+    </class>
+
+    <class name="Order" table="orders">
+        <id name="id">
+            <generator class="native"/>
+        </id>
+        <property name="date"/>
+        <many-to-one name="customer" column="customer_id"/>
+        <list name="lineItems" table="line_items">
+            <key column="order_id"/>
+            <list-index column="line_number"/>
+            <composite-element class="LineItem">
+                <property name="quantity"/>
+                <many-to-one name="product" column="product_id"/>
+            </composite-element>
+        </list>
+    </class>
+
+    <class name="Product" table="products">
+        <id name="id">
+            <generator class="native"/>
+        </id>
+        <property name="serialNumber"/>
+    </class>
+
+</hibernate-mapping>]]></programlisting>
+
+    <para>
+        <literal>customers</literal>, <literal>orders</literal>, <literal>line_items</literal> et
+        <literal>products</literal> contiennent les données de customer, order, order line item et product.
+        <literal>line_items</literal> est aussi la table d'association liant orders à products.
+    </para>
+
+    <programlisting><![CDATA[create table customers (
+    id BIGINT not null generated by default as identity,
+    name VARCHAR(255),
+    primary key (id)
+)
+
+create table orders (
+    id BIGINT not null generated by default as identity,
+    customer_id BIGINT,
+    date TIMESTAMP,
+    primary key (id)
+)
+
+create table line_items (
+    line_number INTEGER not null,
+    order_id BIGINT not null,
+    product_id BIGINT,
+    quantity INTEGER,
+    primary key (order_id, line_number)
+)
+
+create table products (
+    id BIGINT not null generated by default as identity,
+    serialNumber VARCHAR(255),
+    primary key (id)
+)
+
+alter table orders
+    add constraint ordersFK0 foreign key (customer_id) references customers
+alter table line_items
+    add constraint line_itemsFK0 foreign key (product_id) references products
+alter table line_items
+    add constraint line_itemsFK1 foreign key (order_id) references orders]]></programlisting>
+
+    </sect1>
+
+    <sect1 id="misc">
+        <title>Divers mappings d'exemple</title>
+
+        <para>
+            Ces exemples sont tous pris de la suite de tests d'Hibernate. Vous en trouverez beaucoup d'autres.
+            Regardez dans le dossier <literal>test</literal> de la distribution d'Hibernate.
+        </para>
+
+        <para>TODO: put words around this stuff</para>
+
+        <sect2 id="example-mappings-typed-onetone">
+            <title>"Typed" one-to-one association</title>
+<programlisting><![CDATA[<class name="Person">
+    <id name="name"/>
+    <one-to-one name="address"
+            cascade="all">
+        <formula>name</formula>
+        <formula>'HOME'</formula>
+    </one-to-one>
+    <one-to-one name="mailingAddress"
+            cascade="all">
+        <formula>name</formula>
+        <formula>'MAILING'</formula>
+    </one-to-one>
+</class>
+
+<class name="Address" batch-size="2"
+        check="addressType in ('MAILING', 'HOME', 'BUSINESS')">
+    <composite-id>
+        <key-many-to-one name="person"
+                column="personName"/>
+        <key-property name="type"
+                column="addressType"/>
+    </composite-id>
+    <property name="street" type="text"/>
+    <property name="state"/>
+    <property name="zip"/>
+</class>]]></programlisting>
+        </sect2>
+
+        <sect2 id="example-mappings-composite-key">
+            <title>Exemple de clef composée</title>
+<programlisting><![CDATA[<class name="Customer">
+
+    <id name="customerId"
+        length="10">
+        <generator class="assigned"/>
+    </id>
+
+    <property name="name" not-null="true" length="100"/>
+    <property name="address" not-null="true" length="200"/>
+
+    <list name="orders"
+            inverse="true"
+            cascade="save-update">
+        <key column="customerId"/>
+        <index column="orderNumber"/>
+        <one-to-many class="Order"/>
+    </list>
+
+</class>
+
+<class name="Order" table="CustomerOrder" lazy="true">
+    <synchronize table="LineItem"/>
+    <synchronize table="Product"/>
+
+    <composite-id name="id"
+            class="Order$Id">
+        <key-property name="customerId" length="10"/>
+        <key-property name="orderNumber"/>
+    </composite-id>
+
+    <property name="orderDate"
+            type="calendar_date"
+            not-null="true"/>
+
+    <property name="total">
+        <formula>
+            ( select sum(li.quantity*p.price)
+            from LineItem li, Product p
+            where li.productId = p.productId
+                and li.customerId = customerId
+                and li.orderNumber = orderNumber )
+        </formula>
+    </property>
+
+    <many-to-one name="customer"
+            column="customerId"
+            insert="false"
+            update="false"
+            not-null="true"/>
+
+    <bag name="lineItems"
+            fetch="join"
+            inverse="true"
+            cascade="save-update">
+        <key>
+            <column name="customerId"/>
+            <column name="orderNumber"/>
+        </key>
+        <one-to-many class="LineItem"/>
+    </bag>
+
+</class>
+
+<class name="LineItem">
+
+    <composite-id name="id"
+            class="LineItem$Id">
+        <key-property name="customerId" length="10"/>
+        <key-property name="orderNumber"/>
+        <key-property name="productId" length="10"/>
+    </composite-id>
+
+    <property name="quantity"/>
+
+    <many-to-one name="order"
+            insert="false"
+            update="false"
+            not-null="true">
+        <column name="customerId"/>
+        <column name="orderNumber"/>
+    </many-to-one>
+
+    <many-to-one name="product"
+            insert="false"
+            update="false"
+            not-null="true"
+            column="productId"/>
+
+</class>
+
+<class name="Product">
+    <synchronize table="LineItem"/>
+
+    <id name="productId"
+        length="10">
+        <generator class="assigned"/>
+    </id>
+
+    <property name="description"
+        not-null="true"
+        length="200"/>
+    <property name="price" length="3"/>
+    <property name="numberAvailable"/>
+
+    <property name="numberOrdered">
+        <formula>
+            ( select sum(li.quantity)
+            from LineItem li
+            where li.productId = productId )
+        </formula>
+    </property>
+
+</class>]]></programlisting>
+        </sect2>
+
+        <sect2 id="example-mappings-composite-key-manytomany">
+            <title>Many-to-many avec une clef composée partagée</title>
+<programlisting><![CDATA[<class name="User" table="`User`">
+    <composite-id>
+        <key-property name="name"/>
+        <key-property name="org"/>
+    </composite-id>
+    <set name="groups" table="UserGroup">
+        <key>
+            <column name="userName"/>
+            <column name="org"/>
+        </key>
+        <many-to-many class="Group">
+            <column name="groupName"/>
+            <formula>org</formula>
+        </many-to-many>
+    </set>
+</class>
+
+<class name="Group" table="`Group`">
+    <composite-id>
+        <key-property name="name"/>
+        <key-property name="org"/>
+    </composite-id>
+    <property name="description"/>
+    <set name="users" table="UserGroup" inverse="true">
+        <key>
+            <column name="groupName"/>
+            <column name="org"/>
+        </key>
+        <many-to-many class="User">
+            <column name="userName"/>
+            <formula>org</formula>
+        </many-to-many>
+    </set>
+</class>
+]]></programlisting>
+        </sect2>
+
+        <sect2 id="example-mappings-content-discrimination">
+            <title>Contenu basé sur une discrimination</title>
+<programlisting><![CDATA[<class name="Person"
+    discriminator-value="P">
+
+    <id name="id"
+        column="person_id"
+        unsaved-value="0">
+        <generator class="native"/>
+    </id>
+
+
+    <discriminator
+        type="character">
+        <formula>
+            case
+                when title is not null then 'E'
+                when salesperson is not null then 'C'
+                else 'P'
+            end
+        </formula>
+    </discriminator>
+
+    <property name="name"
+        not-null="true"
+        length="80"/>
+
+    <property name="sex"
+        not-null="true"
+        update="false"/>
+
+    <component name="address">
+        <property name="address"/>
+        <property name="zip"/>
+        <property name="country"/>
+    </component>
+
+    <subclass name="Employee"
+        discriminator-value="E">
+            <property name="title"
+                length="20"/>
+            <property name="salary"/>
+            <many-to-one name="manager"/>
+    </subclass>
+
+    <subclass name="Customer"
+        discriminator-value="C">
+            <property name="comments"/>
+            <many-to-one name="salesperson"/>
+    </subclass>
+
+</class>]]></programlisting>
+        </sect2>
+
+        <sect2 id="example-mappings-association-alternatekeys" revision="2">
+            <title>Associations sur des clefs alternées</title>
+<programlisting><![CDATA[<class name="Person">
+
+    <id name="id">
+        <generator class="hilo"/>
+    </id>
+
+    <property name="name" length="100"/>
+
+    <one-to-one name="address"
+        property-ref="person"
+        cascade="all"
+        fetch="join"/>
+
+    <set name="accounts"
+        inverse="true">
+        <key column="userId"
+            property-ref="userId"/>
+        <one-to-many class="Account"/>
+    </set>
+
+    <property name="userId" length="8"/>
+
+</class>
+
+<class name="Address">
+
+    <id name="id">
+        <generator class="hilo"/>
+    </id>
+
+    <property name="address" length="300"/>
+    <property name="zip" length="5"/>
+    <property name="country" length="25"/>
+    <many-to-one name="person" unique="true" not-null="true"/>
+
+</class>
+
+<class name="Account">
+    <id name="accountId" length="32">
+        <generator class="uuid"/>
+    </id>
+
+    <many-to-one name="user"
+        column="userId"
+        property-ref="userId"/>
+
+    <property name="type" not-null="true"/>
+
+</class>]]></programlisting>
+        </sect2>
+
+    </sect1>
+
+</chapter>
+

Copied: core/trunk/documentation/manual/fr-FR/src/main/docbook/content/example_parentchild.xml (from rev 14070, core/trunk/documentation/manual/fr-FR/src/main/docbook/modules/example_parentchild.xml)
===================================================================
--- core/trunk/documentation/manual/fr-FR/src/main/docbook/content/example_parentchild.xml	                        (rev 0)
+++ core/trunk/documentation/manual/fr-FR/src/main/docbook/content/example_parentchild.xml	2007-10-09 18:28:36 UTC (rev 14074)
@@ -0,0 +1,372 @@
+<?xml version="1.0" encoding="iso-8859-1"?>
+<chapter id="example-parentchild">
+    <title>Exemple : Père/Fils</title>
+
+    <para>
+        L'une des premières choses que les nouveaux utilisateurs essaient de faire avec Hibernate est de modéliser
+        une relation père/fils. Il y a deux approches différentes pour cela. Pour un certain nombre de raisons, la méthode la
+        plus courante, en particulier pour les nouveaux utilisateurs, est de modéliser les deux relations <literal>Père</literal>
+        et <literal>Fils</literal> comme des classes entités liées par une association <literal>&lt;one-to-many&gt;</literal> du
+        <literal>Père</literal> vers le <literal>Fils</literal> (l'autre approche est de déclarer le <literal>Fils</literal>
+        comme un <literal>&lt;composite-element&gt;</literal>). Il est évident que le sens de l'association un vers plusieurs
+        (dans Hibernate) est bien moins proche du sens habituel d'une relation père/fils que ne l'est celui d'un
+        élément cmposite. Nous allons vous expliquer comment utiliser une association <emphasis>un vers plusieurs bidirectionnelle
+        avec cascade</emphasis> afin de modéliser efficacement et élégamment une relation père/fils, ce n'est vraiment
+        pas difficile !
+    </para>
+
+    <sect1 id="example-parentchild-collections">
+        <title>Une note à propos des collections</title>
+
+        <para>
+            Les collections Hibernate sont considérées comme étant une partie logique
+            de l'entité dans laquelle elles sont contenues ; jamais des entités qu'elle
+            contient. C'est une distinction crutiale ! Les conséquences sont les suivantes :
+        </para>
+
+        <itemizedlist>
+            <listitem>
+                <para>
+                    Quand nous ajoutons / retirons un objet d'une collection, le numéro de version du
+                    propriétaire de la collection est incrémenté.
+                </para>
+            </listitem>
+            <listitem>
+                <para>
+                    Si un objet qui a été enlevé d'une collection est une instance de type valeur (ex :
+                    élément composite), cet objet cessera d'être persistant et son état sera complètement effacé
+                    de la base de données. Par ailleurs, ajouter une instance de type valeur dans une collection
+                    aura pour conséquence que son état sera immédiatement persistant.
+                </para>
+            </listitem>
+            <listitem>
+                <para>
+                    Si une entité est enlevée d'une collection (association un-vers-plusieurs
+                    ou plusieurs-vers-plusieurs), par défaut, elle ne sera pas effacée. Ce comportement
+                    est complètement logique - une modification de l'un des états internes d'une entité
+                    ne doit pas causer la disparition de l'entité associée !
+                    De même, l'ajout d'une entité dans une collection n'engendre pas,
+                    par défaut, la persistance de cette entité.
+                </para>
+            </listitem>
+        </itemizedlist>
+
+        <para>
+            Le comportement par défaut est donc que l'ajout d'une entité dans une collection créé
+            simplement le lien entre les deux entités, et qu'effacer une entité supprime ce lien.
+            C'est le comportement le plus approprié dans la plupart des cas. Ce comportement n'est
+            cependant pas approprié lorsque la vie du fils est liée au cycle de vie du père.
+        </para>
+
+    </sect1>
+
+    <sect1 id="example-parentchild-bidir">
+        <title>un-vers-plusieurs bidirectionnel</title>
+
+        <para>
+            Supposons que nous ayons une simple association <literal>&lt;one-to-many&gt;</literal>
+            de <literal>Parent</literal> vers <literal>Child</literal>.
+        </para>
+
+        <programlisting><![CDATA[<set name="children">
+                <key column="parent_id"/>
+                <one-to-many class="Child"/>
+            </set>]]></programlisting>
+
+        <para>
+            Si nous executions le code suivant
+        </para>
+
+        <programlisting><![CDATA[Parent p = .....;
+Child c = new Child();
+p.getChildren().add(c);
+session.save(c);
+session.flush();]]></programlisting>
+
+        <para>
+            Hibernate exécuterait deux ordres SQL:
+        </para>
+
+        <itemizedlist>
+            <listitem>
+                <para>un <literal>INSERT</literal> pour créer l'enregistrement pour <literal>c</literal></para>
+            </listitem>
+            <listitem>
+                <para>
+                    un <literal>UPDATE</literal> pour créer le lien de <literal>p</literal> vers
+                    <literal>c</literal>
+                </para>
+            </listitem>
+        </itemizedlist>
+
+        <para>
+            Ceci est non seuleument inefficace, mais viole aussi toute contrainte <literal>NOT NULL</literal> sur
+            la colonne <literal>parent_id</literal>. Nous pouvons réparer la contrainte de nullité
+            en spécifiant <literal>not-null="true"</literal> dans le mapping de la collection :
+        </para>
+
+        <programlisting><![CDATA[<set name="children">
+    <key column="parent_id" not-null="true"/>
+    <one-to-many class="Child"/>
+</set>]]></programlisting>
+
+        <para>
+            Cependant ce n'est pas la solution recommandée.
+        </para>
+
+        <para>
+            La cause sous jacente à ce comportement est que le lien (la clé étrangère <literal>parent_id</literal>) de
+            <literal>p</literal> vers <literal>c</literal> n'est pas considérée comme faisant partie de l'état
+            de l'objet <literal>Child</literal> et n'est donc pas créé par l'<literal>INSERT</literal>.
+            La solution est donc que ce lien fasse partie du mapping de <literal>Child</literal>.
+        </para>
+
+        <programlisting><![CDATA[<many-to-one name="parent" column="parent_id" not-null="true"/>]]></programlisting>
+
+        <para>
+            (Nous avons aussi besoin d'ajouter la propriété <literal>parent</literal> dans la classe <literal>Child</literal>).
+        </para>
+
+        <para>
+            Maintenant que l'état du lien est géré par l'entité <literal>Child</literal>, nous spécifions à la
+            collection de ne pas mettre à jour le lien. Nous utilisons l'attribut <literal>inverse</literal>.
+        </para>
+
+        <programlisting><![CDATA[<set name="children" inverse="true">
+    <key column="parent_id"/>
+    <one-to-many class="Child"/>
+</set>]]></programlisting>
+
+        <para>
+            Le code suivant serait utilisé pour ajouter un nouveau <literal>Child</literal>
+        </para>
+
+        <programlisting><![CDATA[Parent p = (Parent) session.load(Parent.class, pid);
+Child c = new Child();
+c.setParent(p);
+p.getChildren().add(c);
+session.save(c);
+session.flush();]]></programlisting>
+
+        <para>
+            Maintenant, seul un <literal>INSERT</literal> SQL est nécessaire !
+        </para>
+
+        <para>
+            Pour alléger encore un peu les choses, nous devrions créer une méthode <literal>addChild()</literal>
+            dans <literal>Parent</literal>.
+        </para>
+
+        <programlisting><![CDATA[public void addChild(Child c) {
+    c.setParent(this);
+    children.add(c);
+}]]></programlisting>
+
+        <para>
+            Le code d'ajout d'un <literal>Child</literal> serait alors
+        </para>
+
+        <programlisting><![CDATA[Parent p = (Parent) session.load(Parent.class, pid);
+Child c = new Child();
+p.addChild(c);
+session.save(c);
+session.flush();]]></programlisting>
+
+    </sect1>
+
+    <sect1 id="example-parentchild-cascades">
+        <title>Cycle de vie en cascade</title>
+
+        <para>
+            L'appel explicite de <literal>save()</literal> est un peu fastidieux. Nous pouvons
+            simplifier cela en utilisant les cascades.
+        </para>
+
+        <programlisting><![CDATA[<set name="children" inverse="true" cascade="all">
+    <key column="parent_id"/>
+    <one-to-many class="Child"/>
+</set>]]></programlisting>
+
+        <para>
+            Simplifie le code précédent en
+        </para>
+
+        <programlisting><![CDATA[Parent p = (Parent) session.load(Parent.class, pid);
+Child c = new Child();
+p.addChild(c);
+session.flush();]]></programlisting>
+
+        <para>
+            De la même manière, nous n'avons pas à itérer sur les fils lorsque nous sauvons
+            ou effacons un <literal>Parent</literal>. Le code suivant efface <literal>p</literal>
+            et tous ses fils de la base de données.
+        </para>
+
+         <programlisting><![CDATA[Parent p = (Parent) session.load(Parent.class, pid);
+session.delete(p);
+session.flush();]]></programlisting>
+
+         <para>
+             Par contre, ce code
+         </para>
+
+         <programlisting><![CDATA[Parent p = (Parent) session.load(Parent.class, pid);
+Child c = (Child) p.getChildren().iterator().next();
+p.getChildren().remove(c);
+c.setParent(null);
+session.flush();]]></programlisting>
+
+         <para>
+             n'effacera pas <literal>c</literal> de la base de données, il enlèvera seulement
+             le lien vers  <literal>p</literal> (et causera une violation de contrainte
+             <literal>NOT NULL</literal>, dans ce cas).
+             Vous devez explicitement utiliser <literal>delete()</literal> sur <literal>Child</literal>.
+         </para>
+
+         <programlisting><![CDATA[Parent p = (Parent) session.load(Parent.class, pid);
+Child c = (Child) p.getChildren().iterator().next();
+p.getChildren().remove(c);
+session.delete(c);
+session.flush();]]></programlisting>
+
+        <para>
+            Dans notre cas, un <literal>Child</literal> ne peut pas vraiment exister sans son père. Si nous
+            effacons un <literal>Child</literal> de la collection, nous voulons vraiment qu'il soit effacé.
+            Pour cela, nous devons utiliser <literal>cascade="all-delete-orphan"</literal>.
+        </para>
+
+        <programlisting><![CDATA[<set name="children" inverse="true" cascade="all-delete-orphan">
+    <key column="parent_id"/>
+    <one-to-many class="Child"/>
+</set>]]></programlisting>
+
+        <para>
+            A noter : même si le mapping de la collection spécifie <literal>inverse="true"</literal>, les cascades
+            sont toujours assurées par l'itération sur les éléments de la collection. Donc, si vous avez besoin
+            qu'un objet soit enregistré, effacé ou mis à jour par cascade, vous devez l'ajouter dans la colleciton.
+            Il ne suffit pas d'appeler explicitement <literal>setParent()</literal>.
+        </para>
+
+    </sect1>
+
+    <sect1 id="example-parentchild-update">
+        <title>Cascades et <literal>unsaved-value</literal></title>
+
+        <para>
+            Supposons que nous ayons chargé un <literal>Parent</literal> dans une <literal>Session</literal>,
+            que nous l'ayons ensuite modifié et que voulions persiter ces modifications dans une nouvelle session
+            en appelant <literal>update()</literal>.
+            Le <literal>Parent</literal> contiendra une collection de fils et, puisque la cascade est activée,
+            Hibernate a besoin de savoir quels fils viennent d'être instanciés et quels fils proviennent de la base
+            de données. Supposons aussi que <literal>Parent</literal> et <literal>Child</literal> ont tous deux
+            des identifiants du type <literal>Long</literal>.
+            Hibernate utilisera la propriété de l'identifiant et la propriété de la version/horodatage pour déterminer quels fils sont nouveaux
+            (vous pouvez aussi utiliser la propriété version ou timestamp, voir
+            <xref linkend="manipulatingdata-updating-detached"/>).
+            <emphasis>Dans Hibernate3, il n'est plus nécessaire de spécifier
+            une <literal>unsaved-value</literal> explicitement.</emphasis>
+        </para>
+
+        <para>
+            Le code suivant mettra à jour <literal>parent</literal> et <literal>child</literal>
+            et insérera <literal>newChild</literal>.
+        </para>
+
+        <programlisting><![CDATA[//parent et child ont été chargés dans une session précédente
+parent.addChild(child);
+Child newChild = new Child();
+parent.addChild(newChild);
+session.update(parent);
+session.flush();]]></programlisting>
+
+        <para>
+            Ceci est très bien pour des identifiants générés, mais qu'en est-il des identifiants assignés et des
+            identifiants composés ? C'est plus difficile,
+            puisqu'Hibernate ne peut pas utiliser la propriété de l'identifiant pour distinguer un objet
+            nouvellement instancié (avec un identifiant assigné par l'utilisateur) d'un objet chargé dans une session précédente.
+            Dans ce cas, Hibernate utilisera soit la propriété de version ou d'horodatage, soit effectuera vraiment une requête au cache
+            de second niveau, soit, dans le pire des cas, à la base de données, pour voir si la ligne existe.
+        </para>
+
+         <!-- undocumenting
+         <para>
+             There is one further possibility. The <literal>Interceptor</literal> method named
+             <literal>isUnsaved()</literal> lets the application implement its own strategy for distinguishing
+             newly instantiated objects. For example, you could define a base class for your persistent classes.
+         </para>
+
+         <programlisting><![CDATA[public class Persistent {
+    private boolean _saved = false;
+    public void onSave() {
+        _saved=true;
+    }
+    public void onLoad() {
+        _saved=true;
+    }
+    ......
+    public boolean isSaved() {
+        return _saved;
+    }
+}]]></programlisting>
+
+         <para>
+             (The <literal>saved</literal> property is non-persistent.)
+             Now implement <literal>isUnsaved()</literal>, along with <literal>onLoad()</literal>
+             and <literal>onSave()</literal> as follows.
+         </para>
+
+         <programlisting><![CDATA[public Boolean isUnsaved(Object entity) {
+    if (entity instanceof Persistent) {
+        return new Boolean( !( (Persistent) entity ).isSaved() );
+    }
+    else {
+        return null;
+    }
+}
+
+public boolean onLoad(Object entity,
+    Serializable id,
+    Object[] state,
+    String[] propertyNames,
+    Type[] types) {
+
+    if (entity instanceof Persistent) ( (Persistent) entity ).onLoad();
+    return false;
+}
+
+public boolean onSave(Object entity,
+    Serializable id,
+    Object[] state,
+    String[] propertyNames,
+    Type[] types) {
+
+    if (entity instanceof Persistent) ( (Persistent) entity ).onSave();
+    return false;
+}]]></programlisting>
+
+        <para>
+            Don't worry; in Hibernate3 you don't need to write any of this kind of code if you don't want to.
+        </para>
+     -->
+    </sect1>
+
+    <sect1 id="example-parentchild-conclusion">
+        <title>Conclusion</title>
+
+        <para>
+            Il y a quelques principes à maîtriser dans ce chapitre et tout cela peut paraître déroutant la première fois.
+            Cependant, dans la pratique, tout fonctionne parfaitement. La plupart des applications Hibernate utilisent
+            le pattern père / fils.
+        </para>
+
+        <para>
+            Nous avons évoqué une alternative dans le premier paragraphe. Aucun des points traités précédemment n'existe
+            dans le cas d'un mapping <literal>&lt;composite-element&gt;</literal> qui possède exactement la sémantique
+            d'une relation père / fils. Malheureusement, il y a deux grandes limitations pour les classes éléments
+            composites : les éléments composites ne peuvent contenir de collections, et ils ne peuvent être les fils
+            d'entités autres que l'unique parent.
+        </para>
+
+     </sect1>
+
+</chapter>
\ No newline at end of file

Copied: core/trunk/documentation/manual/fr-FR/src/main/docbook/content/example_weblog.xml (from rev 14070, core/trunk/documentation/manual/fr-FR/src/main/docbook/modules/example_weblog.xml)
===================================================================
--- core/trunk/documentation/manual/fr-FR/src/main/docbook/content/example_weblog.xml	                        (rev 0)
+++ core/trunk/documentation/manual/fr-FR/src/main/docbook/content/example_weblog.xml	2007-10-09 18:28:36 UTC (rev 14074)
@@ -0,0 +1,432 @@
+<?xml version="1.0" encoding="iso-8859-1"?>
+<chapter id="example-weblog">
+    <title>Exemple : application Weblog</title>
+
+    <sect1 id="example-weblog-classes">
+        <title>Classes persistantes</title>
+
+        <para>
+            Les classes persistantes representent un weblog, et un article posté
+            dans un weblog. Il seront modélisés comme une relation père/fils
+            standard, mais nous allons utiliser un "bag" trié au lieu d'un set.
+
+        </para>
+
+        <programlisting><![CDATA[package eg;
+
+import java.util.List;
+
+public class Blog {
+    private Long _id;
+    private String _name;
+    private List _items;
+
+    public Long getId() {
+        return _id;
+    }
+    public List getItems() {
+        return _items;
+    }
+    public String getName() {
+        return _name;
+    }
+    public void setId(Long long1) {
+        _id = long1;
+    }
+    public void setItems(List list) {
+        _items = list;
+    }
+    public void setName(String string) {
+        _name = string;
+    }
+}]]></programlisting>
+
+        <programlisting><![CDATA[package eg;
+
+import java.text.DateFormat;
+import java.util.Calendar;
+
+public class BlogItem {
+    private Long _id;
+    private Calendar _datetime;
+    private String _text;
+    private String _title;
+    private Blog _blog;
+
+    public Blog getBlog() {
+        return _blog;
+    }
+    public Calendar getDatetime() {
+        return _datetime;
+    }
+    public Long getId() {
+        return _id;
+    }
+    public String getText() {
+        return _text;
+    }
+    public String getTitle() {
+        return _title;
+    }
+    public void setBlog(Blog blog) {
+        _blog = blog;
+    }
+    public void setDatetime(Calendar calendar) {
+        _datetime = calendar;
+    }
+    public void setId(Long long1) {
+        _id = long1;
+    }
+    public void setText(String string) {
+        _text = string;
+    }
+    public void setTitle(String string) {
+        _title = string;
+    }
+}]]></programlisting>
+
+    </sect1>
+
+    <sect1 id="example-weblog-mappings">
+        <title>Mappings Hibernate</title>
+
+        <para>
+            Le mapping XML doit maintenant être relativement simple à vos yeux.
+        </para>
+
+        <programlisting><![CDATA[<?xml version="1.0"?>
+<!DOCTYPE hibernate-mapping PUBLIC
+    "-//Hibernate/Hibernate Mapping DTD 3.0//EN"
+    "http://hibernate.sourceforge.net/hibernate-mapping-3.0.dtd">
+
+<hibernate-mapping package="eg">
+
+    <class
+        name="Blog"
+        table="BLOGS">
+
+        <id
+            name="id"
+            column="BLOG_ID">
+
+            <generator class="native"/>
+
+        </id>
+
+        <property
+            name="name"
+            column="NAME"
+            not-null="true"
+            unique="true"/>
+
+        <bag
+            name="items"
+            inverse="true"
+            order-by="DATE_TIME"
+            cascade="all">
+
+            <key column="BLOG_ID"/>
+            <one-to-many class="BlogItem"/>
+
+        </bag>
+
+    </class>
+
+</hibernate-mapping>]]></programlisting>
+
+        <programlisting><![CDATA[<?xml version="1.0"?>
+<!DOCTYPE hibernate-mapping PUBLIC
+    "-//Hibernate/Hibernate Mapping DTD 3.0//EN"
+    "http://hibernate.sourceforge.net/hibernate-mapping-3.0.dtd">
+
+<hibernate-mapping package="eg">
+
+    <class
+        name="BlogItem"
+        table="BLOG_ITEMS"
+        dynamic-update="true">
+
+        <id
+            name="id"
+            column="BLOG_ITEM_ID">
+
+            <generator class="native"/>
+
+        </id>
+
+        <property
+            name="title"
+            column="TITLE"
+            not-null="true"/>
+
+        <property
+            name="text"
+            column="TEXT"
+            not-null="true"/>
+
+        <property
+            name="datetime"
+            column="DATE_TIME"
+            not-null="true"/>
+
+        <many-to-one
+            name="blog"
+            column="BLOG_ID"
+            not-null="true"/>
+
+    </class>
+
+</hibernate-mapping>]]></programlisting>
+
+    </sect1>
+
+    <sect1 id="example-weblog-code">
+        <title>Code Hibernate</title>
+
+        <para>
+            La classe suivante montre quelques utilisations que nous pouvons faire
+            de ces classes.
+        </para>
+
+        <programlisting><![CDATA[package eg;
+
+import java.util.ArrayList;
+import java.util.Calendar;
+import java.util.Iterator;
+import java.util.List;
+
+import org.hibernate.HibernateException;
+import org.hibernate.Query;
+import org.hibernate.Session;
+import org.hibernate.SessionFactory;
+import org.hibernate.Transaction;
+import org.hibernate.cfg.Configuration;
+import org.hibernate.tool.hbm2ddl.SchemaExport;
+
+public class BlogMain {
+
+    private SessionFactory _sessions;
+
+    public void configure() throws HibernateException {
+        _sessions = new Configuration()
+            .addClass(Blog.class)
+            .addClass(BlogItem.class)
+            .buildSessionFactory();
+    }
+
+    public void exportTables() throws HibernateException {
+        Configuration cfg = new Configuration()
+            .addClass(Blog.class)
+            .addClass(BlogItem.class);
+        new SchemaExport(cfg).create(true, true);
+    }
+
+    public Blog createBlog(String name) throws HibernateException {
+
+        Blog blog = new Blog();
+        blog.setName(name);
+        blog.setItems( new ArrayList() );
+
+        Session session = _sessions.openSession();
+        Transaction tx = null;
+        try {
+            tx = session.beginTransaction();
+            session.persist(blog);
+            tx.commit();
+        }
+        catch (HibernateException he) {
+            if (tx!=null) tx.rollback();
+            throw he;
+        }
+        finally {
+            session.close();
+        }
+        return blog;
+    }
+
+    public BlogItem createBlogItem(Blog blog, String title, String text)
+                        throws HibernateException {
+
+        BlogItem item = new BlogItem();
+        item.setTitle(title);
+        item.setText(text);
+        item.setBlog(blog);
+        item.setDatetime( Calendar.getInstance() );
+        blog.getItems().add(item);
+
+        Session session = _sessions.openSession();
+        Transaction tx = null;
+        try {
+            tx = session.beginTransaction();
+            session.update(blog);
+            tx.commit();
+        }
+        catch (HibernateException he) {
+            if (tx!=null) tx.rollback();
+            throw he;
+        }
+        finally {
+            session.close();
+        }
+        return item;
+    }
+
+    public BlogItem createBlogItem(Long blogid, String title, String text)
+                        throws HibernateException {
+
+        BlogItem item = new BlogItem();
+        item.setTitle(title);
+        item.setText(text);
+        item.setDatetime( Calendar.getInstance() );
+
+        Session session = _sessions.openSession();
+        Transaction tx = null;
+        try {
+            tx = session.beginTransaction();
+            Blog blog = (Blog) session.load(Blog.class, blogid);
+            item.setBlog(blog);
+            blog.getItems().add(item);
+            tx.commit();
+        }
+        catch (HibernateException he) {
+            if (tx!=null) tx.rollback();
+            throw he;
+        }
+        finally {
+            session.close();
+        }
+        return item;
+    }
+
+    public void updateBlogItem(BlogItem item, String text)
+                    throws HibernateException {
+
+        item.setText(text);
+
+        Session session = _sessions.openSession();
+        Transaction tx = null;
+        try {
+            tx = session.beginTransaction();
+            session.update(item);
+            tx.commit();
+        }
+        catch (HibernateException he) {
+            if (tx!=null) tx.rollback();
+            throw he;
+        }
+        finally {
+            session.close();
+        }
+    }
+
+    public void updateBlogItem(Long itemid, String text)
+                    throws HibernateException {
+
+        Session session = _sessions.openSession();
+        Transaction tx = null;
+        try {
+            tx = session.beginTransaction();
+            BlogItem item = (BlogItem) session.load(BlogItem.class, itemid);
+            item.setText(text);
+            tx.commit();
+        }
+        catch (HibernateException he) {
+            if (tx!=null) tx.rollback();
+            throw he;
+        }
+        finally {
+            session.close();
+        }
+    }
+
+    public List listAllBlogNamesAndItemCounts(int max)
+                    throws HibernateException {
+
+        Session session = _sessions.openSession();
+        Transaction tx = null;
+        List result = null;
+        try {
+            tx = session.beginTransaction();
+            Query q = session.createQuery(
+                "select blog.id, blog.name, count(blogItem) " +
+                "from Blog as blog " +
+                "left outer join blog.items as blogItem " +
+                "group by blog.name, blog.id " +
+                "order by max(blogItem.datetime)"
+            );
+            q.setMaxResults(max);
+            result = q.list();
+            tx.commit();
+        }
+        catch (HibernateException he) {
+            if (tx!=null) tx.rollback();
+            throw he;
+        }
+        finally {
+            session.close();
+        }
+        return result;
+    }
+
+    public Blog getBlogAndAllItems(Long blogid)
+                    throws HibernateException {
+
+        Session session = _sessions.openSession();
+        Transaction tx = null;
+        Blog blog = null;
+        try {
+            tx = session.beginTransaction();
+            Query q = session.createQuery(
+                "from Blog as blog " +
+                "left outer join fetch blog.items " +
+                "where blog.id = :blogid"
+            );
+            q.setParameter("blogid", blogid);
+            blog  = (Blog) q.uniqueResult();
+            tx.commit();
+        }
+        catch (HibernateException he) {
+            if (tx!=null) tx.rollback();
+            throw he;
+        }
+        finally {
+            session.close();
+        }
+        return blog;
+    }
+
+    public List listBlogsAndRecentItems() throws HibernateException {
+
+        Session session = _sessions.openSession();
+        Transaction tx = null;
+        List result = null;
+        try {
+            tx = session.beginTransaction();
+            Query q = session.createQuery(
+                "from Blog as blog " +
+                "inner join blog.items as blogItem " +
+                "where blogItem.datetime > :minDate"
+            );
+
+            Calendar cal = Calendar.getInstance();
+            cal.roll(Calendar.MONTH, false);
+            q.setCalendar("minDate", cal);
+
+            result = q.list();
+            tx.commit();
+        }
+        catch (HibernateException he) {
+            if (tx!=null) tx.rollback();
+            throw he;
+        }
+        finally {
+            session.close();
+        }
+        return result;
+    }
+}]]></programlisting>
+
+    </sect1>
+
+</chapter>
+

Copied: core/trunk/documentation/manual/fr-FR/src/main/docbook/content/filters.xml (from rev 14070, core/trunk/documentation/manual/fr-FR/src/main/docbook/modules/filters.xml)
===================================================================
--- core/trunk/documentation/manual/fr-FR/src/main/docbook/content/filters.xml	                        (rev 0)
+++ core/trunk/documentation/manual/fr-FR/src/main/docbook/content/filters.xml	2007-10-09 18:28:36 UTC (rev 14074)
@@ -0,0 +1,135 @@
+<?xml version="1.0" encoding="iso-8859-1"?>
+<chapter id="filters">
+    <title>Filtrer les données</title>
+
+    <para>
+        Hibernate3 fournit une nouvelle approche innovatrice pour gérer des données
+        avec des règles de "visibilité". Un <emphasis>filtre Hibernate</emphasis> est un filtre
+        global, nommé, paramétré qui peut être activé ou désactivé pour une session Hibernate
+        particulière.
+    </para>
+
+    <sect1 id="objectstate-filters">
+        <title>Filtres Hibernate</title>
+
+        <para>
+            Hibernate3 ajoute la capacité de prédéfinir des critères de filtre et d'attacher ces
+            filtres à une classe ou à une collection. Un critère de filtre est la faculté de définir
+            une clause de restriction très similaire à l'attribut "where" existant disponible sur
+            une classe et divers éléments d'une collection. Mis à part que ces conditions de filtre
+            peuvent être paramétrées. L'application peut alors prendre la décision à l'exécution
+            si des filtres donnés devraient être activés et quels devraient être leurs paramètres.
+            Des filtres peuvent être utilisés comme des vues de base de données, mais paramétrées
+            dans l'application.
+        </para>
+
+        <para>
+            Afin d'utiliser des filtres, ils doivent d'abord être définis, puis attachés aux éléments
+            de mapping appropriés. Pour définir un filtre, utilisez l'élément <literal>&lt;filter-def/&gt;</literal>
+            dans un élément <literal>&lt;hibernate-mapping/&gt;</literal> :
+        </para>
+
+        <programlisting><![CDATA[<filter-def name="myFilter">
+    <filter-param name="myFilterParam" type="string"/>
+</filter-def>]]></programlisting>
+
+        <para>
+            Puis, ce filtre peut être attaché à une classe :
+        </para>
+
+        <programlisting><![CDATA[<class name="myClass" ...>
+    ...
+    <filter name="myFilter" condition=":myFilterParam = MY_FILTERED_COLUMN"/>
+</class>]]></programlisting>
+
+        <para>
+            ou à une collection :
+        </para>
+
+        <programlisting><![CDATA[<set ...>
+    <filter name="myFilter" condition=":myFilterParam = MY_FILTERED_COLUMN"/>
+</set>]]></programlisting>
+
+        <para>
+            ou même aux deux (ou à plusieurs de chaque) en même temps.
+        </para>
+
+        <para>
+            Les méthodes sur <literal>Session</literal> sont : <literal>enableFilter(String filterName)</literal>,
+            <literal>getEnabledFilter(String filterName)</literal>, et <literal>disableFilter(String filterName)</literal>.
+            Par défaut, les filtres <emphasis>ne sont pas</emphasis> activés pour une session donnée ;
+            ils doivent être explicitement activés en appelant la méthode
+            <literal>Session.enabledFilter()</literal>, laquelle retourne une instance de l'interface
+            <literal>Filter</literal>. Utiliser le simple filtre défini au-dessus ressemblerait à :
+        </para>
+
+        <programlisting><![CDATA[session.enableFilter("myFilter").setParameter("myFilterParam", "some-value");]]></programlisting>
+
+        <para>
+            Notez que des méthodes sur l'interface org.hibernate.Filter autorisent le chaînage de beaucoup
+            de méthodes communes d'Hibernate.
+        </para>
+
+        <para>
+            Un exemple complet, utilisant des données temporelles avec une structure de date
+            d'enregistrement effectif :
+        </para>
+
+        <programlisting><![CDATA[<filter-def name="effectiveDate">
+    <filter-param name="asOfDate" type="date"/>
+</filter-def>
+
+<class name="Employee" ...>
+...
+    <many-to-one name="department" column="dept_id" class="Department"/>
+    <property name="effectiveStartDate" type="date" column="eff_start_dt"/>
+    <property name="effectiveEndDate" type="date" column="eff_end_dt"/>
+...
+    <!--
+        Note that this assumes non-terminal records have an eff_end_dt set to
+        a max db date for simplicity-sake
+    -->
+    <filter name="effectiveDate"
+            condition=":asOfDate BETWEEN eff_start_dt and eff_end_dt"/>
+</class>
+
+<class name="Department" ...>
+...
+    <set name="employees" lazy="true">
+        <key column="dept_id"/>
+        <one-to-many class="Employee"/>
+        <filter name="effectiveDate"
+                condition=":asOfDate BETWEEN eff_start_dt and eff_end_dt"/>
+    </set>
+</class>]]></programlisting>
+
+        <para>
+            Puis, afin de s'assurer que vous pouvez toujours récupérer les enregistrements actuellement
+            effectifs, activez simplement le filtre sur la session avant de récupérer des données des
+            employés :
+        </para>
+
+<programlisting><![CDATA[Session session = ...;
+session.enabledFilter("effectiveDate").setParameter("asOfDate", new Date());
+List results = session.createQuery("from Employee as e where e.salary > :targetSalary")
+         .setLong("targetSalary", new Long(1000000))
+         .list();
+]]></programlisting>
+
+        <para>
+            Dans le HQL ci-dessus, bien que nous ayons seulement mentionné une contrainte de
+            salaire sur les resultats, à cause du filtre activé, la requête retournera seulement
+            les employés actuellement actifs qui ont un salaire supérieur à un million de dollars.
+        </para>
+
+        <para>
+            A noter : si vous prévoyez d'utiliser des filtres avec des jointures externes (soit
+            à travers HQL, soit par le chargement) faites attention à la direction de l'expression
+            de condition. Il est plus sûr de la positionner pour les jointures externes à gauche ;
+            en général, placez le paramètre d'abord, suivi du(des) nom(s) de colonne après l'opérateur.
+        </para>
+
+    </sect1>
+
+</chapter>
+

Copied: core/trunk/documentation/manual/fr-FR/src/main/docbook/content/inheritance_mapping.xml (from rev 14070, core/trunk/documentation/manual/fr-FR/src/main/docbook/modules/inheritance_mapping.xml)
===================================================================
--- core/trunk/documentation/manual/fr-FR/src/main/docbook/content/inheritance_mapping.xml	                        (rev 0)
+++ core/trunk/documentation/manual/fr-FR/src/main/docbook/content/inheritance_mapping.xml	2007-10-09 18:28:36 UTC (rev 14074)
@@ -0,0 +1,483 @@
+<?xml version="1.0" encoding="iso-8859-1"?>
+<chapter id="inheritance">
+    <title>Mapping d'héritage de classe</title>
+
+    <sect1 id="inheritance-strategies" revision="3">
+        <title>Les trois stratégies</title>
+
+        <para>
+            Hibernate supporte les trois stratégies d'héritage de base :
+        </para>
+
+        <itemizedlist>
+        <listitem>
+        <para>
+            une table par hiérarchie de classe (table per class hierarchy)
+        </para>
+        </listitem>
+        <listitem>
+        <para>
+            une table par classe fille (table per subclass)
+        </para>
+        </listitem>
+        <listitem>
+        <para>
+            une table par classe concrète (table per concrete class)
+        </para>
+        </listitem>
+        </itemizedlist>
+
+        <para>
+            Hibernate supporte en plus une quatrièmestratégie, légèrement différente, qui supporte le polymorphisme :
+        </para>
+
+        <itemizedlist>
+        <listitem>
+        <para>
+            le polymorphisme implicite
+        </para>
+        </listitem>
+        </itemizedlist>
+
+        <para>
+            Il est possible d'utiliser différentes stratégies de mapping pour différentes branches d'une même
+            hiérarchie d'héritage, et alors d'employer le polymorphisme implicite pour réaliser le
+            polymorphisme à travers toute la hiérarchie. Pourtant, Hibernate ne supporte pas de mélanger
+            des mappings <literal>&lt;subclass&gt;</literal> et
+            <literal>&lt;joined-subclass&gt;</literal> et <literal>&lt;union-subclass&gt;</literal>
+            pour le même élément <literal>&lt;class&gt;</literal> racine.
+            Il est possible de mélanger ensemble les stratégies d'une table par hiérarchie et d'une
+            table par sous-classe, pour le même élément <literal>&lt;class&gt;</literal>, en combinant
+            les éléments <literal>&lt;subclass&gt;</literal> et <literal>&lt;join&gt;</literal> (voir dessous).
+        </para>
+
+        <para>
+            Il est possible de définir des mappings de <literal>subclass</literal>, <literal>union-subclass</literal>,
+            et <literal>joined-subclass</literal> dans des documents de mapping séparés, directement sous
+            <literal>hibernate-mapping</literal>. Ceci vous permet d'étendre une hiérarchie de classe juste en
+            ajoutant un nouveau fichier de mapping. Vous devez spécifier un attribut <literal>extends</literal>
+            dans le mapping de la sous-classe, en nommant une super-classe précédemment mappée. Note :
+            précédemment cette foncionnalité rendait l'ordre des documents de mapping important. Depuis
+            Hibernate3, l'ordre des fichier de mapping n'importe plus lors de l'utilisation du mot-clef "extends".
+            L'ordre à l'intérieur d'un simple fichier de mapping impose encore de définir les classes mères
+            avant les classes filles.
+         </para>
+
+         <programlisting><![CDATA[
+ <hibernate-mapping>
+     <subclass name="DomesticCat" extends="Cat" discriminator-value="D">
+          <property name="name" type="string"/>
+     </subclass>
+ </hibernate-mapping>]]></programlisting>
+
+
+        <sect2 id="inheritance-tableperclass" >
+        <title>Une table par hiérarchie de classe</title>
+
+        <para>
+            Supposons que nous ayons une interface <literal>Payment</literal>, implémentée
+            par <literal>CreditCardPayment</literal>, <literal>CashPayment</literal>,
+            <literal>ChequePayment</literal>. La stratégie une table par hiérarchie serait :
+        </para>
+
+        <programlisting><![CDATA[<class name="Payment" table="PAYMENT">
+    <id name="id" type="long" column="PAYMENT_ID">
+        <generator class="native"/>
+    </id>
+    <discriminator column="PAYMENT_TYPE" type="string"/>
+    <property name="amount" column="AMOUNT"/>
+    ...
+    <subclass name="CreditCardPayment" discriminator-value="CREDIT">
+        <property name="creditCardType" column="CCTYPE"/>
+        ...
+    </subclass>
+    <subclass name="CashPayment" discriminator-value="CASH">
+        ...
+    </subclass>
+    <subclass name="ChequePayment" discriminator-value="CHEQUE">
+        ...
+    </subclass>
+</class>]]></programlisting>
+
+        <para>
+            Une seule table est requise. Une grande limitation de cette
+            stratégie est que les colonnes déclarées par les classes filles, telles que <literal>CCTYPE</literal>,
+            ne peuvent avoir de contrainte <literal>NOT NULL</literal>.
+        </para>
+
+        </sect2>
+
+        <sect2 id="inheritance-tablepersubclass">
+        <title>Une table par classe fille</title>
+
+        <para>
+            La stratégie une table par classe fille serait :
+        </para>
+
+        <programlisting><![CDATA[<class name="Payment" table="PAYMENT">
+    <id name="id" type="long" column="PAYMENT_ID">
+        <generator class="native"/>
+    </id>
+    <property name="amount" column="AMOUNT"/>
+    ...
+    <joined-subclass name="CreditCardPayment" table="CREDIT_PAYMENT">
+        <key column="PAYMENT_ID"/>
+        <property name="creditCardType" column="CCTYPE"/>
+        ...
+    </joined-subclass>
+    <joined-subclass name="CashPayment" table="CASH_PAYMENT">
+        <key column="PAYMENT_ID"/>
+        ...
+    </joined-subclass>
+    <joined-subclass name="ChequePayment" table="CHEQUE_PAYMENT">
+        <key column="PAYMENT_ID"/>
+        ...
+    </joined-subclass>
+</class>]]></programlisting>
+
+        <para>
+            Quatre tables sont requises. Les trois tables des classes filles ont
+            une clé primaire associée à la table classe mère (le modèle relationnel
+            est une association un-vers-un).
+        </para>
+
+        </sect2>
+
+        <sect2 id="inheritance-tablepersubclass-discriminator" revision="2">
+        <title>Une table par classe fille, en utilisant un discriminant</title>
+
+        <para>
+            Notez que l'implémentation Hibernate de la stratégie un table par
+            classe fille ne nécessite pas de colonne discriminante dans la table
+            classe mère. D'autres implémentations de mappers Objet/Relationnel utilisent
+            une autre implémentation de la stratégie une table par classe fille qui nécessite
+            une colonne de type discriminant dans la table de la classe mère. L'approche
+            prise par Hibernate est plus difficile à implémenter mais plus correcte
+        d'une point de vue relationnel. Si vous aimeriez utiliser
+            une colonne discriminante avec la stratégie d'une table par classe fille, vous pourriez combiner
+            l'utilisation de <literal>&lt;subclass&gt;</literal> et
+            <literal>&lt;join&gt;</literal>, comme suit :
+        </para>
+
+        <programlisting><![CDATA[<class name="Payment" table="PAYMENT">
+    <id name="id" type="long" column="PAYMENT_ID">
+        <generator class="native"/>
+    </id>
+    <discriminator column="PAYMENT_TYPE" type="string"/>
+    <property name="amount" column="AMOUNT"/>
+    ...
+    <subclass name="CreditCardPayment" discriminator-value="CREDIT">
+        <join table="CREDIT_PAYMENT">
+            <key column="PAYMENT_ID"/>
+            <property name="creditCardType" column="CCTYPE"/>
+            ...
+        </join>
+    </subclass>
+    <subclass name="CashPayment" discriminator-value="CASH">
+        <join table="CASH_PAYMENT">
+            <key column="PAYMENT_ID"/>
+            ...
+        </join>
+    </subclass>
+    <subclass name="ChequePayment" discriminator-value="CHEQUE">
+        <join table="CHEQUE_PAYMENT" fetch="select">
+            <key column="PAYMENT_ID"/>
+            ...
+        </join>
+    </subclass>
+</class>]]></programlisting>
+
+        <para>
+            La déclaration optionnelle <literal>fetch="select"</literal> indique à Hibernate
+            de ne pas récupérer les données de la classe fille <literal>ChequePayment</literal> par une jointure externe lors des requêtes sur la classe mère.
+        </para>
+
+        </sect2>
+
+        <sect2 id="inheritance-mixing-tableperclass-tablepersubclass">
+            <title>Mélange d'une table par hiérarchie de classe avec une table par classe fille</title>
+
+        <para>
+            Vous pouvez même mélanger les stratégies d'une table par hiérarchie de classe et d'une table par classe fille en utilisant cette approche :
+        </para>
+
+        <programlisting><![CDATA[<class name="Payment" table="PAYMENT">
+    <id name="id" type="long" column="PAYMENT_ID">
+        <generator class="native"/>
+    </id>
+    <discriminator column="PAYMENT_TYPE" type="string"/>
+    <property name="amount" column="AMOUNT"/>
+    ...
+    <subclass name="CreditCardPayment" discriminator-value="CREDIT">
+        <join table="CREDIT_PAYMENT">
+            <property name="creditCardType" column="CCTYPE"/>
+            ...
+        </join>
+    </subclass>
+    <subclass name="CashPayment" discriminator-value="CASH">
+        ...
+    </subclass>
+    <subclass name="ChequePayment" discriminator-value="CHEQUE">
+        ...
+    </subclass>
+</class>]]></programlisting>
+
+        <para>
+            Pour importe laquelle de ces stratégies, une association polymorphique vers la classe racine
+            <literal>Payment</literal> est mappée en utilisant <literal>&lt;many-to-one&gt;</literal>.
+        </para>
+
+        <programlisting><![CDATA[<many-to-one name="payment" column="PAYMENT_ID" class="Payment"/>]]></programlisting>
+
+        </sect2>
+
+        <sect2 id="inheritance-tableperconcrete" revision="2">
+        <title>Une table par classe concrète</title>
+
+        <para>
+            Il y a deux manières d'utiliser la stratégie d'une table par classe concrète. La première
+            est d'employer <literal>&lt;union-subclass&gt;</literal>.
+        </para>
+
+        <programlisting><![CDATA[<class name="Payment">
+    <id name="id" type="long" column="PAYMENT_ID">
+        <generator class="sequence"/>
+    </id>
+    <property name="amount" column="AMOUNT"/>
+    ...
+    <union-subclass name="CreditCardPayment" table="CREDIT_PAYMENT">
+        <property name="creditCardType" column="CCTYPE"/>
+        ...
+    </union-subclass>
+    <union-subclass name="CashPayment" table="CASH_PAYMENT">
+        ...
+    </union-subclass>
+    <union-subclass name="ChequePayment" table="CHEQUE_PAYMENT">
+        ...
+    </union-subclass>
+</class>]]></programlisting>
+
+        <para>
+            Trois tables sont nécessaires pour les classes filles. Chaque table définit des colonnes
+            pour toutes les propriétés de la classe, incluant les propriétés héritéés.
+        </para>
+
+        <para>
+            La limitation de cette approche est que si une propriété est mappée sur la classe mère, le nom
+            de la colonne doit être le même pour toutes les classes filles. (Nous pourrions être plus souple
+            dans une future version d'Hibernate).
+            La stratégie du générateur d'identifiant n'est pas permise dans l'héritage de classes filles par
+            union, en effet la valeur (NdT : seed) de la clef primaire
+            doit être partagée par toutes les classes filles "union" d'une hiérarchie.
+        </para>
+
+        <para>
+            Si votre classe mère est abstraite, mappez la avec <literal>abstract="true"</literal>.
+            Bien sûr, si elle n'est pas abstraite, une table supplémentaire (par défaut,
+            <literal>PAYMENT</literal> dans l'exemple ci-dessus) est requise pour contenir des instances
+            de la classe mère.
+        </para>
+
+        </sect2>
+
+        <sect2 id="inheritance-tableperconcreate-polymorphism">
+        <title>Une table par classe concrète, en utilisant le polymorphisme implicite</title>
+
+        <para>
+            Une approche alternative est l'emploi du polymorphisme implicite :
+        </para>
+
+        <programlisting><![CDATA[<class name="CreditCardPayment" table="CREDIT_PAYMENT">
+    <id name="id" type="long" column="CREDIT_PAYMENT_ID">
+        <generator class="native"/>
+    </id>
+    <property name="amount" column="CREDIT_AMOUNT"/>
+    ...
+</class>
+
+<class name="CashPayment" table="CASH_PAYMENT">
+    <id name="id" type="long" column="CASH_PAYMENT_ID">
+        <generator class="native"/>
+    </id>
+    <property name="amount" column="CASH_AMOUNT"/>
+    ...
+</class>
+
+<class name="ChequePayment" table="CHEQUE_PAYMENT">
+    <id name="id" type="long" column="CHEQUE_PAYMENT_ID">
+        <generator class="native"/>
+    </id>
+    <property name="amount" column="CHEQUE_AMOUNT"/>
+    ...
+</class>]]></programlisting>
+
+        <para>
+            Notez que nulle part nous ne mentionnons l'interface <literal>Payment</literal> explicitement.
+            Notez aussi que des propriétés de <literal>Payment</literal> sont mappées dans
+            chaque classe fille. Si vous voulez éviter des duplications, considérez l'utilisation des
+            entités XML (cf. <literal>[ &lt;!ENTITY allproperties SYSTEM "allproperties.xml"&gt; ]</literal>
+            dans la déclaration du <literal>DOCTYPE</literal> et <literal>&amp;allproperties;</literal> dans le mapping).
+        </para>
+
+        <para>
+            L'inconvénient de cette approche est qu'Hibernate ne génère pas d'<literal>UNION</literal>s SQL
+            lors de l'exécution des requêtes polymorphiques.
+        </para>
+
+        <para>
+            Pour cette stratégie de mapping, une association polymorphique pour <literal>Payment</literal>
+            est habituellement mappée en utilisant <literal>&lt;any&gt;</literal>.
+        </para>
+
+        <programlisting><![CDATA[<any name="payment" meta-type="string" id-type="long">
+    <meta-value value="CREDIT" class="CreditCardPayment"/>
+    <meta-value value="CASH" class="CashPayment"/>
+    <meta-value value="CHEQUE" class="ChequePayment"/>
+    <column name="PAYMENT_CLASS"/>
+    <column name="PAYMENT_ID"/>
+</any>]]></programlisting>
+
+        </sect2>
+
+        <sect2 id="inheritace-mixingpolymorphism">
+        <title>Mélange du polymorphisme implicite avec d'autres mappings d'héritage</title>
+
+        <para>
+            Il y a une chose supplémentaire à noter à propos de ce mapping. Puisque les classes filles sont
+            chacune mappées avec leur propre élément <literal>&lt;class&gt;</literal> (et puisque
+            <literal>Payment</literal> est juste une interface), chaque classe fille pourrait
+            facilement faire partie d'une autre hiérarchie
+            d'héritage ! (Et vous pouvez encore faire des requêtes polymorphiques pour l'interface <literal>Payment</literal>).
+       </para>
+
+        <programlisting><![CDATA[<class name="CreditCardPayment" table="CREDIT_PAYMENT">
+    <id name="id" type="long" column="CREDIT_PAYMENT_ID">
+        <generator class="native"/>
+    </id>
+    <discriminator column="CREDIT_CARD" type="string"/>
+    <property name="amount" column="CREDIT_AMOUNT"/>
+    ...
+    <subclass name="MasterCardPayment" discriminator-value="MDC"/>
+    <subclass name="VisaPayment" discriminator-value="VISA"/>
+</class>
+
+<class name="NonelectronicTransaction" table="NONELECTRONIC_TXN">
+    <id name="id" type="long" column="TXN_ID">
+        <generator class="native"/>
+    </id>
+    ...
+    <joined-subclass name="CashPayment" table="CASH_PAYMENT">
+        <key column="PAYMENT_ID"/>
+        <property name="amount" column="CASH_AMOUNT"/>
+        ...
+    </joined-subclass>
+    <joined-subclass name="ChequePayment" table="CHEQUE_PAYMENT">
+        <key column="PAYMENT_ID"/>
+        <property name="amount" column="CHEQUE_AMOUNT"/>
+        ...
+    </joined-subclass>
+</class>]]></programlisting>
+
+        <para>
+            Encore une fois, nous ne mentionnons pas explicitement <literal>Payment</literal>.
+            Si nous exécutons une requête sur l'interface <literal>Payment</literal> - par
+            exemple, <literal>from Payment</literal> - Hibernate retournera
+            automatiquement les instances de <literal>CreditCardPayment</literal>
+            (et ses classes filles puisqu'elles implémentent aussi <literal>Payment</literal>),
+            <literal>CashPayment</literal> et <literal>ChequePayment</literal> mais pas
+            les instances de <literal>NonelectronicTransaction</literal>.
+        </para>
+
+        </sect2>
+
+    </sect1>
+
+    <sect1 id="inheritance-limitations">
+        <title>Limitations</title>
+
+        <para>
+            Il y a certaines limitations à l'approche du "polymorphisme implicite"
+            pour la stratégie de mapping d'une table par classe concrète.
+            Il y a plutôt moins de limitations restrictives aux mappings <literal>&lt;union-subclass&gt;</literal>.
+        </para>
+
+        <para>
+            La table suivante montre les limitations des mappings d'une table par classe concrète, et du polymorphisme implicite, dans Hibernate.
+        </para>
+
+        <table frame="topbot">
+            <title>Caractéristiques du mapping d'héritage</title>
+            <tgroup cols='8' align='left' colsep='1' rowsep='1'>
+            <colspec colname='c1' colwidth="1*"/>
+            <colspec colname='c2' colwidth="1*"/>
+            <colspec colname='c3' colwidth="1*"/>
+            <colspec colname='c4' colwidth="1*"/>
+            <colspec colname='c5' colwidth="1*"/>
+            <colspec colname='c6' colwidth="1*"/>
+            <colspec colname='c7' colwidth="1*"/>
+            <colspec colname='c8' colwidth="1*"/>
+            <thead>
+            <row>
+              <entry>Stratégie d'héritage</entry>
+              <entry>many-to-one polymorphique</entry>
+              <entry>one-to-one polymorphique</entry>
+              <entry>one-to-many polymorphique</entry>
+              <entry>many-to-many polymorphique</entry>
+              <entry><literal>load()/get()</literal> polymorphique</entry>
+              <entry>Requêtes polymorphiques</entry>
+              <entry>Jointures polymorphiques</entry>
+              <entry>Récupération par jointure externe</entry>
+            </row>
+            </thead>
+            <tbody>
+            <row>
+                <entry>une table par hiérarchie de classe</entry>
+                <entry><literal>&lt;many-to-one&gt;</literal></entry>
+                <entry><literal>&lt;one-to-one&gt;</literal></entry>
+                <entry><literal>&lt;one-to-many&gt;</literal></entry>
+                <entry><literal>&lt;many-to-many&gt;</literal></entry>
+                <entry><literal>s.get(Payment.class, id)</literal></entry>
+                <entry><literal>from Payment p</literal></entry>
+                <entry><literal>from Order o join o.payment p</literal></entry>
+                <entry><emphasis>supportée</emphasis></entry>
+            </row>
+            <row>
+                <entry>une table par classe fille</entry>
+                <entry><literal>&lt;many-to-one&gt;</literal></entry>
+                <entry><literal>&lt;one-to-one&gt;</literal></entry>
+                <entry><literal>&lt;one-to-many&gt;</literal></entry>
+                <entry><literal>&lt;many-to-many&gt;</literal></entry>
+                <entry><literal>s.get(Payment.class, id)</literal></entry>
+                <entry><literal>from Payment p</literal></entry>
+                <entry><literal>from Order o join o.payment p</literal></entry>
+                <entry><emphasis>supportée</emphasis></entry>
+            </row>
+            <row>
+                <entry>une table par classe concrète (union-subclass)</entry>
+                <entry><literal>&lt;many-to-one&gt;</literal></entry>
+                <entry><literal>&lt;one-to-one&gt;</literal></entry>
+                <entry><literal>&lt;one-to-many&gt;</literal> (pour <literal>inverse="true"</literal> seulement)</entry>
+                <entry><literal>&lt;many-to-many&gt;</literal></entry>
+                <entry><literal>s.get(Payment.class, id)</literal></entry>
+                <entry><literal>from Payment p</literal></entry>
+                <entry><literal>from Order o join o.payment p</literal></entry>
+                <entry><emphasis>supportée</emphasis></entry>
+            </row>
+            <row>
+                <entry>une table par classe concrète (polymorphisme implicite)</entry>
+                <entry><literal>&lt;any&gt;</literal></entry>
+                <entry><emphasis>non supporté</emphasis></entry>
+                <entry><emphasis>non supporté</emphasis></entry>
+                <entry><literal>&lt;many-to-any&gt;</literal></entry>
+                <entry><literal>s.createCriteria(Payment.class).add( Restrictions.idEq(id) ).uniqueResult()</literal></entry>
+                <entry><literal>from Payment p</literal></entry>
+                <entry><emphasis>non supportées</emphasis></entry>
+                <entry><emphasis>non supportée</emphasis></entry>
+            </row>
+            </tbody>
+            </tgroup>
+        </table>
+
+    </sect1>
+
+</chapter>

Copied: core/trunk/documentation/manual/fr-FR/src/main/docbook/content/performance.xml (from rev 14070, core/trunk/documentation/manual/fr-FR/src/main/docbook/modules/performance.xml)
===================================================================
--- core/trunk/documentation/manual/fr-FR/src/main/docbook/content/performance.xml	                        (rev 0)
+++ core/trunk/documentation/manual/fr-FR/src/main/docbook/content/performance.xml	2007-10-09 18:28:36 UTC (rev 14074)
@@ -0,0 +1,1451 @@
+<?xml version="1.0" encoding="iso-8859-1"?>
+<chapter id="performance">
+    <title>Améliorer les performances</title>
+
+    <sect1 id="performance-fetching" revision="2">
+        <title>Stratégies de chargement</title>
+
+        <para>
+            Une <emphasis>stratégie de chargement</emphasis> est une stratégie qu'Hibernate va
+            utiliser pour récupérer des objets associés si l'application à besoin de naviguer à 
+            travers une association.
+            Les stratégies de chargement peuvent être déclarées dans les méta-données de l'outil
+            de mapping objet relationnel ou surchargées par une requête de type HQL ou <literal>Criteria</literal>
+            particulière.
+        </para>
+
+        <para>
+            Hibernate3 définit les stratégies de chargement suivantes :
+        </para>
+
+        <itemizedlist>
+             <listitem>
+                <para>
+                    <emphasis>Chargement par jointure</emphasis> - Hibernate récupère 
+                    l'instance associée ou la collection dans un même <literal>SELECT</literal>,
+                    en utilisant un <literal>OUTER JOIN</literal>.
+                </para>
+            </listitem>
+            <listitem>
+                <para>
+                    <emphasis>Chargement par select</emphasis> - Un second <literal>SELECT</literal>
+                    est utilisé pour récupérer l'instance associée ou la collection. A moins
+                    que vous ne désactiviez explicitement le chargement tardif en spécifiant
+                    <literal>lazy="false"</literal>, ce second select ne sera exécuté que lorsque
+                    vous accéderez réellement à l'association.
+                </para>
+            </listitem>
+            <listitem>
+                <para>
+                    <emphasis>Chargement par sous-select</emphasis> - Un second <literal>SELECT</literal>
+                    est utilisé pour récupérer les associations pour toutes les entités récupérées dans
+                    une requête ou un chargement préalable. A moins
+                    que vous ne désactiviez explicitement le chargement tardif en spécifiant
+                    <literal>lazy="false"</literal>, ce second select ne sera exécuté que lorsque
+                    vous accéderez réellement à l'association.
+                </para>
+            </listitem>
+            <listitem>
+                <para>
+                    <emphasis>Chargement par lot</emphasis> - Il s'agit d'une stratégie d'optimisation
+                    pour le chargement par select - Hibernate récupère un lot
+                    d'instances ou de collections en un seul <literal>SELECT</literal> en spécifiant
+                    une liste de clé primaire ou de clé étrangère.
+                </para>
+            </listitem>
+        </itemizedlist>
+        
+        <para>
+            Hibernate fait également la distinction entre :
+        </para>
+
+        <itemizedlist>
+             <listitem>
+                <para>
+                    <emphasis>Chargement immédiat</emphasis> - Une association, une collection ou
+                    un attribut est chargé immédiatement lorsque l'objet auquel appartient cet
+                    élément est chargé.
+                </para>
+            </listitem>
+            <listitem>
+                <para>
+                    <emphasis>Chargement tardif d'une collection</emphasis> - Une collection est
+                    chargée lorque l'application invoque une méthode sur cette collection (il s'agit
+                    du mode de chargement par défaut pour les collections).
+                </para>
+            </listitem>
+            <listitem>
+                <para>
+                    <emphasis>Chargement "super tardif" d'une collection</emphasis> - les
+                    éléments de la collection sont récupérés individuellement depuis la base de données
+                    lorsque nécessaire.
+                    Hibernate essaie de ne pas charger toute la collection en mémoire sauf si cela est
+                    absolument nécessaire (bien adapté aux très grandes collections).
+                </para>
+            </listitem>
+            <listitem>
+                <para>
+                    <emphasis>Chargement par proxy</emphasis> - une association vers un seul
+                    objet est chargée lorsqu'une méthode autre que le getter sur l'identifiant est
+                    appelée sur l'objet associé. 
+                </para>
+            </listitem>
+            <listitem>
+                <para>
+                    <emphasis>Chargement "sans proxy"</emphasis> - une association vers un seul objet
+                    est chargée lorsque l'on accède à cet objet. Par rapport au chargement par proxy,
+                    cette approche est moins tardif (l'association est quand même chargée même
+                    si on n'accède qu'à l'identifiant) mais plus transparente car il n'y a pas de proxy
+                    visible dans l'application. Cette approche requiert une instrumentation du bytecode
+                    à la compilation et est rarement nécessaire.
+                </para>
+            </listitem>
+            <listitem>
+                <para>
+                    <emphasis>Chargement tardif des attributs</emphasis> - Un attribut ou un
+                    objet associé seul est chargé lorsque l'on y accède. Cette approche requiert 
+                    une instrumentation du bytecode à la compilation et est rarement nécessaire.
+                </para>
+            </listitem>
+        </itemizedlist>
+        
+        <para>
+            Nous avons ici deux notions orthogonales : <emphasis>quand</emphasis> l'association est
+            chargée et <emphasis>comment</emphasis> (quelle requête SQL est utilisée). Il ne faut
+            pas confondre les deux. Le mode de chargement est utilisé pour améliorer les performances.
+            On peut utiliser le mode tardif pour définir un contrat sur quelles données sont toujours
+            accessibles sur une instance détachée d'une classe particulière.
+        </para>
+ 
+        <sect2 id="performance-fetching-lazy">
+            <title>Travailler avec des associations chargées tardivement</title>
+            
+            <para>
+                Par défaut, Hibernate3 utilise le chargement tardif par select pour les collections
+                et le chargement tardif par proxy pour les associations vers un seul objet.
+                Ces valeurs par défaut sont valables pour la plupart des associations dans la
+                plupart des applications.
+            </para>
+            
+            <para>
+                <emphasis>Note :</emphasis> si vous définissez
+                <literal>hibernate.default_batch_fetch_size</literal>, Hibernate va utiliser l'optimisation
+                du chargement par lot pour le chargement tardif (cette optimisation peut aussi
+                être activée à un niveau de granularité plus fin).
+            </para>
+            
+            <para>
+                Cependant, le chargement tardif pose un problème qu'il faut connaitre. L'accès à 
+                une association définie comme "tardive", hors du contexte d'une session hibernate
+                ouverte, va conduire à une exception. Par exemple :
+            </para>
+        
+            <programlisting><![CDATA[s = sessions.openSession();
+Transaction tx = s.beginTransaction();
+            
+User u = (User) s.createQuery("from User u where u.name=:userName")
+    .setString("userName", userName).uniqueResult();
+Map permissions = u.getPermissions();
+
+tx.commit();
+s.close();
+
+Integer accessLevel = (Integer) permissions.get("accounts");  // Error!]]></programlisting>
+
+            <para>
+                Etant donné que la collection des permissions n'a pas été initialisée
+                avant que la <literal>Session</literal> soit fermée, la collection n'est
+                pas capable de se charger. <emphasis>Hibernate ne supporte pas le chargement
+                tardif pour des objets détachés</emphasis>. La solution à ce problème est de
+                déplacer le code qui lit la collection avant le "commit" de la transaction.
+            </para>
+    
+            <para>
+                Une autre alternative est d'utiliser une collection ou une association non
+                "tardive" en spécifiant <literal>lazy="false"</literal> dans le mapping de
+                l'association.
+                Cependant il est prévu que le chargement tardif soit utilisé pour quasiment
+                toutes les collections ou associations. Si vous définissez trop d'associtions
+                non "tardives" dans votre modèle objet, Hibernate va finir par devoir charger
+                toute la base de données en mémoire à chaque transaction !
+            </para>
+    
+            <para>
+                D'un autre côté, on veut souvent choisir un chargement par jointure (qui est par
+                défaut non tardif) à la place du chargement par select dans une transaction particulière.
+                Nous allons maintenant voir comment adapter les stratégies de chargement. Dans Hibernate3
+                les mécanismes pour choisir une stratégie de chargement sont identiques que
+                l'on ait une association vers un objet simple ou vers une collection.
+            </para>
+        
+        </sect2>
+        
+        <sect2 id="performance-fetching-custom" revision="4">
+            <title>Personnalisation des stratégies de chargement</title>
+            
+            <para>
+                Le chargement par select (mode par défaut) est très vulnérable au problème du
+                N+1 selects, du coup vous pouvez avoir envie d'activer le chargement par jointure
+                dans les fichiers de mapping :
+            </para>
+            
+            <programlisting><![CDATA[<set name="permissions" 
+            fetch="join">
+    <key column="userId"/>
+    <one-to-many class="Permission"/>
+</set]]></programlisting>
+
+           <programlisting><![CDATA[<many-to-one name="mother" class="Cat" fetch="join"/>]]></programlisting>
+
+            <para>
+                La stratégie de chargement définie à l'aide du mot <literal>fetch</literal> dans les fichiers
+                de mapping affecte :
+            </para>
+            
+        <itemizedlist>
+             <listitem>
+                <para>
+                    La récupération via <literal>get()</literal> ou <literal>load()</literal>
+                </para>
+            </listitem>
+            <listitem>
+                <para>
+                    La récupération implicite lorsque l'on navigue à travers une association
+                </para>
+            </listitem>
+            <listitem>
+                <para>
+                    Les requêtes de type <literal>Criteria</literal>
+                </para>
+            </listitem>
+            <listitem>
+                <para>
+                    Les requêtes HQL si l'on utilise le chargement par <literal>subselect</literal>
+                </para>
+            </listitem>
+        </itemizedlist>
+
+            <para>
+                Quelle que soit la stratégie de chargement que vous utilisez, la partie du graphe
+                d'objets qui est définie comme non "tardive" sera chargée en mémoire. Cela peut
+                mener à l'exécution de plusieurs selects successifs pour une seule requête HQL.
+            </para>
+
+            <para>
+                On n'utilise pas souvent les documents de mapping pour adapter le chargement.
+                Au lieu de cela, on conserve le comportement par défaut et on le surcharge pour
+                une transaction particulière en utilisant <literal>left join fetch</literal>
+                dans les requêtes HQL. Cela indique à hibernate à Hibernate de charger l'association
+                de manière agressive lors du premier select en utilisant une jointure externe.
+                Dans l'API Criteria vous pouvez utiliser la méthode 
+                <literal>setFetchMode(FetchMode.JOIN)</literal>
+            </para>
+            
+            <para>
+                Si vous ne vous sentez pas prêt à modifier la stratégie de chargement utilisé
+                par <literal>get()</literal> ou <literal>load()</literal>, vous pouvez juste
+                utiliser une requête de type <literal>Criteria</literal>  comme par exemple :
+            </para>
+            
+            <programlisting><![CDATA[User user = (User) session.createCriteria(User.class)
+                .setFetchMode("permissions", FetchMode.JOIN)
+                .add( Restrictions.idEq(userId) )
+                .uniqueResult();]]></programlisting>
+                
+            <para>
+                (Il s'agit de l'équivalent pour Hibernate de ce que d'autres outils de mapping
+                appellent un "fetch plan" ou "plan de chargement")
+            </para>
+
+            <para>
+                Une autre manière complètement différente d'éviter le problème des N+1 selects
+                est d'utiliser le cache de second niveau.
+            </para>
+
+        </sect2>
+
+        <sect2 id="performance-fetching-proxies" revision="2">
+            <title>Proxys pour des associations vers un seul objet</title>
+
+            <para>
+                Le chargement tardif des collections est implémenté par Hibernate en utilisant
+                ses propres implémentations pour des collections persistantes. Si l'on veut un
+                chargement tardif pour des associations vers un seul objet métier il faut utiliser
+                un autre mécanisme. L'entité qui est pointée par l'association doit être masquée
+                derrière un proxy. Hibernate implémente l'initialisation tardive des proxys sur des
+                objets persistents via une mise à jour à chaud du bytecode (à l'aide de l'excellente
+                librairie CGLIB).
+            </para>
+
+            <para>
+                Par défaut, Hibernate génère des proxys (au démarrage) pour toutes les classes
+                persistantes et les utilise pour activer le chargement tardif des associations
+                <literal>many-to-one</literal> et <literal>one-to-one</literal>.
+            </para>
+
+            <para>
+                Le fichier de mapping peut déclarer une interface qui sera utilisée par le proxy
+                d'interfaçage pour cette classe à l'aide de l'attribut <literal>proxy</literal>.
+                Par défaut Hibernate utilises une sous classe de la classe persistante.
+                <emphasis>Il faut que les classes pour lesquelles on ajoute un proxy implémentent
+                un constructeur par défaut de visibilité au moins package. Ce constructeur est
+                recommandé pour toutes les classes persistantes !</emphasis>
+            </para>
+
+
+
+            <para>
+                Il y a quelques précautions à prendre lorsque l'on étend cette approche à des classes
+          polymorphiques, exemple :
+            </para>
+
+            <programlisting><![CDATA[<class name="Cat" proxy="Cat">
+        ......
+        <subclass name="DomesticCat" proxy="DomesticCat">
+            .....
+        </subclass>
+    </class>]]></programlisting>
+
+        <para>
+            Tout d'abord, les instances de <literal>Cat</literal> ne pourront jamais être "castées"
+        en <literal>DomesticCat</literal>, même si l'instance sous jacente est une instance 
+        de <literal>DomesticCat</literal> :
+        </para>
+        
+        <programlisting><![CDATA[Cat cat = (Cat) session.load(Cat.class, id);  // instancie un proxy (n'interroge pas la base de données)
+if ( cat.isDomesticCat() ) {                  // interroge la base de données pour initialiser le proxy
+    DomesticCat dc = (DomesticCat) cat;       // Erreur !
+    ....
+}]]></programlisting>
+    
+        <para>
+            Deuxièmement, il est possible de casser la notion d'<literal>==</literal> des proxy.
+        </para>
+            
+        <programlisting><![CDATA[Cat cat = (Cat) session.load(Cat.class, id);            // instancie un proxy Cat
+DomesticCat dc = 
+    (DomesticCat) session.load(DomesticCat.class, id);  // acquiert un nouveau proxy DomesticCat
+System.out.println(cat==dc);                            // faux]]></programlisting>
+        
+        <para>
+            Cette situation n'est pas si mauvaise qu'il n'y parait. Même si nous avons deux
+        références à deux objets proxys différents, l'instance de base sera quand même le même objet :
+        </para>
+    
+        <programlisting><![CDATA[cat.setWeight(11.0);  // interroge la base de données pour initialiser le proxy
+System.out.println( dc.getWeight() );  // 11.0]]></programlisting>
+
+        <para>
+            Troisièmement, vous ne pourrez pas utiliser un proxy CGLIB pour une classe <literal>final</literal>
+        ou pour une classe contenant la moindre méthode <literal>final</literal>.
+        </para>
+        
+        <para>
+            Enfin, si votre objet persistant obtient une ressource à l'instanciation (par
+        example dans les initialiseurs ou dans le contructeur par défaut), alors ces ressources
+        seront aussi obtenues par le proxy. La classe proxy est vraiment une sous classe de la classe
+        persistante.
+        </para>
+        
+        <para>
+            Ces problèmes sont tous dus aux limitations fondamentales du modèle d'héritage unique de Java.
+        Si vous souhaitez éviter ces problèmes, vos classes persistantes doivent chacune implémenter
+        une interface qui déclare ses méthodes métier. Vous devriez alors spécifier ces interfaces
+        dans le fichier de mapping :
+        </para>
+
+        <programlisting><![CDATA[<class name="CatImpl" proxy="Cat">
+    ......
+    <subclass name="DomesticCatImpl" proxy="DomesticCat">
+        .....
+    </subclass>
+</class>]]></programlisting>
+
+        <para>
+            où <literal>CatImpl</literal> implémente l'interface <literal>Cat</literal> et <literal>DomesticCatImpl</literal> 
+        implémente l'interface <literal>DomesticCat</literal>. Ainsi, des proxys pour les instances de 
+        <literal>Cat</literal> et <literal>DomesticCat</literal> pourraient être retournées par <literal>load()</literal> 
+        ou <literal>iterate()</literal> (Notez que <literal>list()</literal> ne retourne généralement pas de proxy).
+        </para>
+
+        <programlisting><![CDATA[Cat cat = (Cat) session.load(CatImpl.class, catid);
+Iterator iter = session.createQuery("from CatImpl as cat where cat.name='fritz'").iterate();
+Cat fritz = (Cat) iter.next();]]></programlisting>
+        
+        <para>
+            Les relations sont aussi initialisées tardivement. Ceci signifie que vous 
+        devez déclarer chaque propriété comme étant de type <literal>Cat</literal>, 
+        et non <literal>CatImpl</literal>.
+        </para>
+        
+        <para>
+            Certaines opérations ne nécessitent pas l'initialisation du proxy
+        </para>
+        
+        <itemizedlist spacing="compact">
+            <listitem>
+                <para>
+                    <literal>equals()</literal>, si la classe persistante ne surcharge pas
+                    <literal>equals()</literal>
+                </para>
+            </listitem>
+            <listitem>
+                <para>
+                    <literal>hashCode()</literal>, si la classe persistante ne surcharge pas
+                    <literal>hashCode()</literal>
+                </para>
+            </listitem>
+            <listitem>
+                <para>
+                    Le getter de l'identifiant
+                </para>
+            </listitem>
+        </itemizedlist>
+            
+        <para>
+            Hibernate détectera les classes qui surchargent <literal>equals()</literal> ou
+            <literal>hashCode()</literal>.
+        </para>
+
+        <para>
+            Eh choisissant <literal>lazy="no-proxy"</literal> au lieu de <literal>lazy="proxy"</literal>
+            qui est la valeur par défaut, il est possible d'éviter les problèmes liés au transtypage.
+            Il faudra alors une instrumentation du bytecode à la compilation et toutes les opérations
+            résulterons immédiatement en une initialisation du proxy.
+        </para>
+
+        </sect2>
+
+        <sect2 id="performance-fetching-initialization"  revision="1">
+            <title>Initialisation des collections et des proxys</title>
+
+            <para>
+                Une exception de type <literal>LazyInitializationException</literal> sera renvoyée par hibernate
+                si une collection ou un proxy non initialisé est accédé en dehors de la portée de la <literal>Session</literal>,
+                e.g. lorsque l'entité à laquelle appartient la collection ou qui a une référence vers le proxy est
+                dans l'état "détachée".
+            </para>
+
+        <para>
+            Parfois, nous devons nous assurer qu'un proxy ou une collection est initialisée avant de 
+            fermer la <literal>Session</literal>. Bien sûr, nous pouvons toujours forcer l'initialisation
+            en appelant par exemple <literal>cat.getSex()</literal> ou <literal>cat.getKittens().size()</literal>.
+            Mais ceci n'est pas très lisible pour les personnes parcourant le code et n'est pas très générique.
+        </para>
+        
+        <para>
+            Les méthodes statiques <literal>Hibernate.initialize()</literal> et <literal>Hibernate.isInitialized()</literal>
+            fournissent à l'application un moyen de travailler avec des proxys ou des collections initialisés.
+            <literal>Hibernate.initialize(cat)</literal> forcera l'initialisation d'un proxy de <literal>cat</literal>, 
+            si tant est que sa <literal>Session</literal> est ouverte. <literal>Hibernate.initialize( cat.getKittens() )</literal> 
+            a le même effet sur la collection kittens. 
+        </para>
+
+            <para>
+                Une autre option est de conserver la <literal>Session</literal> ouverte jusqu'à
+                ce que toutes les collections et tous les proxys aient été chargés. Dans certaines
+                architectures applicatives, particulièrement celles ou le code d'accès aux données
+                via hiberante et le code qui utilise ces données sont dans des couches applicatives
+                différentes ou des processus physiques différents, il peut devenir problématique
+                de garantir que la <literal>Session</literal> est ouverte lorsqu'une collection
+                est initialisée. Il y a deux moyens de traiter ce problème :
+            </para>
+
+            <itemizedlist>
+                <listitem>
+                    <para>
+                        Dans une application web, un filtre de servlet peut être utilisé pour
+                        fermer la <literal>Session</literal> uniquement lorsque la requête
+                        a été entièrement traitée, lorsque le rendu de la vue est fini
+                        (il s'agit du pattern <emphasis>Open Session in View</emphasis>).
+                        Bien sûr, cela demande plus d'attention à la bonne gestion des exceptions
+                        de l'application. Il est d'une importance vitale que la <literal>Session</literal>
+                        soit fermée et la transaction terminée avant que l'on rende la main à l'utilisateur
+                        même si une exception survient durant le traitement de la vue. 
+                        Voir le wiki Hibernate pour des exemples sur le pattern
+                        "Open Session in View".
+                    </para>
+                </listitem>
+                <listitem>
+                    <para>
+                        Dans une application avec une couche métier séparée, la couche contenant
+                        la logique métier doit "préparer" toutes les collections qui seront
+                        nécessaires à la couche web avant de retourner les données. Cela signifie
+                        que la couche métier doit charger toutes les données et retourner toutes
+                        les données déjà initialisées à la couche de présentation/web pour un
+                        cas d'utilisation donné. En général l'application appelle la méthode
+                        <literal>Hibernate.initialize()</literal> pour chaque collection nécessaire
+                        dans la couche web (cet appel doit être fait avant la fermeture de la session)
+                        ou bien récupère les collections de manière agressive à l'aide d'une requête
+                        HQL avec une clause <literal>FETCH</literal> ou à l'aide du mode
+                        <literal>FetchMode.JOIN</literal> pour une requête de type <literal>Criteria</literal>.
+                        Cela est en général plus facile si vous utilisez le pattern <emphasis>Command</emphasis>
+                        plutôt que <emphasis>Session Facade</emphasis>.
+                    </para>
+                </listitem>
+                <listitem>
+                    <para>
+                        Vous pouvez également attacher à une <literal>Session</literal> un objet chargé
+                        au préalable à l'aide des méthodes <literal>merge()</literal> ou <literal>lock()</literal>
+                        avant d'accéder aux collections (ou aux proxys) non initialisés. Non, Hibernate ne
+                        fait pas, et ne doit pas faire, cela automatiquement car cela pourrait introduire
+                        une sémantique transactionnelle ad hoc.
+                    </para>
+                </listitem>
+            </itemizedlist>
+
+            <para>
+                Parfois, vous ne voulez pas initialiser une grande collection mais vous avez quand même
+                besoin d'informations sur elle (comme sa taille) ou un sous ensemble de ses données
+            </para>
+
+            <para>
+                Vous pouvez utiliser un filtre de collection pour récupérer sa taille sans l'initialiser :
+            </para>
+
+            <programlisting><![CDATA[( (Integer) s.createFilter( collection, "select count(*)" ).list().get(0) ).intValue()]]></programlisting>
+
+            <para>
+                La méthode <literal>createFilter()</literal> est également utilisée pour récupérer
+                de manière efficace des sous ensembles d'une collection sans avoir besoin de l'initialiser
+                dans son ensemble.
+            </para>
+
+            <programlisting><![CDATA[s.createFilter( lazyCollection, "").setFirstResult(0).setMaxResults(10).list();]]></programlisting>
+
+        </sect2>
+
+
+      <sect2 id="performance-fetching-batch">
+        <title>Utiliser le chargement par lot</title>
+
+        <para>
+            Pour améliorer les performances, Hibernate peut utiliser le chargement par lot
+            ce qui veut dire qu'Hibernate peut charger plusieurs proxys (ou collections) non initialisés en une seule 
+            requête lorsque l'on accède à l'un de ces proxys. Le chargement par lot est une optimisation 
+            intimement liée à la stratégie de chargement tardif par select. Il y a deux moyens d'activer le  
+            chargement par lot : au niveau de la classe et au niveau de la collection.
+        </para>
+
+        <para>
+            Le chargement par lot pour les classes/entités est plus simple à comprendre. Imaginez que vous ayez la
+            situation suivante à l'exécution : vous avez 25 instances de <literal>Cat</literal> 
+            chargées dans une <literal>Session</literal>, chaque <literal>Cat</literal> a une référence 
+            à son <literal>owner</literal>, une <literal>Person</literal>.
+            La classe <literal>Person</literal> est mappée avec un proxy, <literal>lazy="true"</literal>. 
+            Si vous itérez sur tous les cats et appelez <literal>getOwner()</literal> sur chacun d'eux, 
+            Hibernate exécutera par défaut 25 <literal>SELECT</literal>, pour charger les owners
+            (initialiser le proxy). Vous pouvez paramétrer ce comportement en spécifiant une 
+            <literal>batch-size</literal> (taille du lot) dans le mapping de <literal>Person</literal> :
+        </para>
+
+            <programlisting><![CDATA[<class name="Person" batch-size="10">...</class>]]></programlisting>
+
+        <para>
+            Hibernate exécutera désormais trois requêtes, en chargeant respectivement 10, 
+            10, et 5 entités.
+        </para>
+
+        <para>
+            Vous pouvez aussi activer le chargement par lot pour les collections. Par exemple, 
+            si chaque <literal>Person</literal> a une collection chargée tardivement de 
+            <literal>Cat</literal>s, et que 10 personnes sont actuellement chargées dans la 
+            <literal>Session</literal>, itérer sur toutes les persons générera 10 <literal>SELECT</literal>s,
+            un pour chaque appel de <literal>getCats()</literal>. Si vous activez le chargement par lot pour la
+            collection <literal>cats</literal> dans le mapping de <literal>Person</literal>, Hibernate pourra
+            précharger les collections :
+        </para>
+
+        <programlisting><![CDATA[<class name="Person">
+    <set name="cats" batch-size="3">
+        ...
+    </set>
+</class>]]></programlisting>
+
+        <para>
+            Avec une taille de lot (<literal>batch-size</literal>) de 3, Hibernate chargera 
+        respectivement 3, 3, 3, et 1 collections en quatre <literal>SELECT</literal>s. 
+        Encore une fois, la valeur de l'attribut dépend du nombre de collections
+        non initialisées dans une <literal>Session</literal> particulière.
+        </para>
+
+        <para>
+            Le chargement par lot de collections est particulièrement utile si vous avez des 
+        arborescenses récursives d'éléments (typiquement, le schéma facture de 
+        matériels). (Bien qu'un <emphasis>sous ensemble</emphasis> ou un 
+        <emphasis>chemin matérialisé</emphasis> est sans doute une meilleure option pour
+        des arbres principalement en lecture.)
+        </para>
+
+        </sect2>
+
+        <sect2 id="performance-fetching-subselect">
+            <title>Utilisation du chargement par sous select</title>
+
+            <para>
+                Si une collection ou un proxy vers un objet doit être chargé, Hibernate va tous les
+                charger en ré-exécutant la requête orignial dans un sous select. Cela fonctionne de la
+                même manière que le chargement par lot sans la possibilité de fragmenter le chargement.
+            </para>
+            
+            <!-- TODO: Write more about this -->
+
+        </sect2>
+        
+        <sect2 id="performance-fetching-lazyproperties">
+            <title>Utiliser le chargement tardif des propriétés</title>
+
+            <para>
+                Hibernate3 supporte le chargement tardif de propriétés individuelles. La technique
+                d'optimisation est également connue sous le nom de <emphasis>fetch groups</emphasis> (groupes
+                de chargement). Il faut noter qu'il s'agit principalement d'une fonctionnalité marketing
+                car en pratique l'optimisation de la lecture d'un enregistrement est beaucoup plus importante
+                que l'optimisation de la lecture d'une colonne. Cependant, la restriction du chargement à
+                certaines colonnes peut être pratique dans des cas extrèmes, lorsque des tables "legacy"
+                possèdent des centaines de colonnes et que le modèle de données ne peut pas être amélioré.
+            </para>
+
+            <para>
+                Pour activer le chargement tardif d'une propriété, il faut mettre l'attribut <literal>lazy</literal>
+                sur une propriété particulière du mapping :
+            </para>
+
+            <programlisting><![CDATA[<class name="Document">
+       <id name="id">
+        <generator class="native"/>
+    </id>
+    <property name="name" not-null="true" length="50"/>
+    <property name="summary" not-null="true" length="200" lazy="true"/>
+    <property name="text" not-null="true" length="2000" lazy="true"/>
+</class>]]></programlisting>
+
+            <para>
+                Le chargement tardif des propriétés requiert une instrumentation du bytecode lors de la
+                compilation ! Si les classes persistantes ne sont pas instrumentées, Hibernate ignorera de
+                manière silencieuse le mode tardif et retombera dans le mode de chargement immédiat.
+            </para>
+
+            <para>
+                Pour l'instrumentation du bytecode vous pouvez utiliser la tâche Ant suivante :
+            </para>
+
+            <programlisting><![CDATA[<target name="instrument" depends="compile">
+    <taskdef name="instrument" classname="org.hibernate.tool.instrument.InstrumentTask">
+        <classpath path="${jar.path}"/>
+        <classpath path="${classes.dir}"/>
+        <classpath refid="lib.class.path"/>
+    </taskdef>
+
+    <instrument verbose="true">
+        <fileset dir="${testclasses.dir}/org/hibernate/auction/model">
+            <include name="*.class"/>
+        </fileset>
+    </instrument>
+</target>]]></programlisting>
+
+            <para>
+                Une autre façon (meilleure ?) pour éviter de lire plus de colonnes que
+                nécessaire au moins pour des transactions en lecture seule est d'utiliser
+                les fonctionnalités de projection des requêtes HQL ou Criteria. Cela évite
+                de devoir instrumenter le bytecode à la compilation et est certainement une
+                solution préférable.
+            </para>
+            
+            <para>
+                Vous pouvez forcer le mode de chargement agressif des propriétés en utilisant
+                <literal>fetch all properties</literal> dans les requêts HQL.
+            </para>
+
+        </sect2>
+    </sect1>    
+
+    <sect1 id="performance-cache" revision="1">
+        <title>Le cache de second niveau</title>
+
+        <para>
+            Une <literal>Session</literal> Hibernate est un cache de niveau transactionnel 
+        des données persistantes. Il est possible de configurer un cache de cluster ou de JVM 
+        (de niveau <literal>SessionFactory</literal> pour être exact) défini classe par classe 
+        et collection par collection. Vous pouvez même utiliser votr choix de cache
+        en implémentant le pourvoyeur (provider) associé.
+        Faites attention, les caches ne sont jamais avertis des modifications faites 
+        dans la base de données par d'autres applications (ils peuvent cependant être 
+        configurés pour régulièrement expirer les données en cache).
+        </para>
+        
+        <para>
+            Par défaut, Hibernate utilise EHCache comme cache de niveau JVM (le support 
+        de JCS est désormais déprécié et sera enlevé des futures versions d'Hibernate).
+        Vous pouvez choisir une autre implémentation en spécifiant le nom de la classe qui 
+        implémente <literal>org.hibernate.cache.CacheProvider</literal> en utilisant 
+        la propriété <literal>hibernate.cache.provider_class</literal>.
+        </para>
+
+        <table frame="topbot" id="cacheproviders" revision="1">
+            <title>Fournisseur de cache</title>
+            <tgroup cols='5' align='left' colsep='1' rowsep='1'>
+            <colspec colname='c1' colwidth="1*"/>
+            <colspec colname='c2' colwidth="3*"/>
+            <colspec colname='c3' colwidth="1*"/>
+            <colspec colname='c4' colwidth="1*"/>
+            <colspec colname='c5' colwidth="1*"/>
+            <thead>
+            <row>
+              <entry>Cache</entry>
+              <entry>Classe pourvoyeuse</entry>
+              <entry>Type</entry>
+              <entry>Support en Cluster</entry>
+              <entry>Cache de requêtes supporté</entry>
+            </row>
+            </thead>
+            <tbody>
+            <row>
+                <entry>Hashtable (ne pas utiliser en production)</entry>
+                <entry><literal>org.hibernate.cache.HashtableCacheProvider</literal></entry>
+                <entry>mémoire</entry>
+                <entry></entry>
+                <entry>oui</entry>
+            </row>
+            <row>
+                <entry>EHCache</entry>
+                <entry><literal>org.hibernate.cache.EhCacheProvider</literal></entry>
+                <entry>mémoire, disque</entry>
+                <entry></entry>
+                <entry>oui</entry>
+            </row>
+            <row>
+                <entry>OSCache</entry>
+                <entry><literal>org.hibernate.cache.OSCacheProvider</literal></entry>
+                <entry>mémoire, disque</entry>
+                <entry>oui (invalidation de cluster)</entry>
+                <entry>oui</entry>
+            </row>
+            <row>
+                <entry>SwarmCache</entry>
+                <entry><literal>org.hibernate.cache.SwarmCacheProvider</literal></entry>
+                <entry>en cluster (multicast ip)</entry>
+                <entry>oui (invalidation de cluster)</entry>
+                <entry></entry>
+            </row>
+            <row>
+                <entry>JBoss TreeCache</entry>
+                <entry><literal>org.hibernate.cache.TreeCacheProvider</literal></entry>
+                <entry>en cluster (multicast ip), transactionnel</entry>
+                <entry>oui (replication)</entry>
+                <entry>oui (horloge sync. nécessaire)</entry>
+            </row>
+            </tbody>
+            </tgroup>
+        </table>
+
+        <sect2 id="performance-cache-mapping" revision="2">
+            <title>Mapping de Cache</title>
+
+            <para>
+                L'élément <literal>&lt;cache&gt;</literal> d'une classe ou d'une collection à
+        la forme suivante :
+            </para>
+
+            <programlistingco>
+                <areaspec>
+                    <area id="cache1" coords="2 70"/>
+                    <area id="cache2" coords="3 70"/>
+                    <area id="cache3" coords="4 70"/>
+                </areaspec>
+                <programlisting><![CDATA[<cache 
+    usage="transactional|read-write|nonstrict-read-write|read-only"
+    region="RegionName"
+    include="all|non-lazy"
+/>]]></programlisting>
+                <calloutlist>
+                    <callout arearefs="cache1">
+                        <para>
+                            <literal>usage</literal> (requis) spécifie la stratégie de cache :
+                            <literal>transactionel</literal>,
+                            <literal>lecture-écriture</literal>,
+                            <literal>lecture-écriture non stricte</literal> ou
+                            <literal>lecture seule</literal>
+                        </para>
+                    </callout>                   
+                    <callout arearefs="cache2">
+                        <para>
+                            <literal>region</literal> (optionnel, par défaut il s'agit du nom
+                            de la classe ou du nom de role de la collection) spécifie le nom de la
+                            région du cache de second niveau
+                        </para>
+                    </callout>
+                    <callout arearefs="cache3">
+                        <para>
+                            <literal>include</literal> (optionnel, par défaut <literal>all</literal>)
+                            <literal>non-lazy</literal> spécifie que les propriétés des entités mappées avec 
+                            <literal>lazy="true"</literal> ne doivent pas être mises en cache lorsque
+                            le chargement tardif des attributs est activé.
+                        </para>
+                    </callout>
+                </calloutlist>
+            </programlistingco>
+            
+            <para>
+                Alternativement (voir préférentiellement), vous pouvez spécifier les éléments 
+        <literal>&lt;class-cache&gt;</literal> et <literal>&lt;collection-cache&gt;</literal> 
+        dans <literal>hibernate.cfg.xml</literal>.
+            </para>
+            
+            <para>
+                L'attribut <literal>usage</literal> spécifie une <emphasis>stratégie de concurrence d'accès au cache</emphasis>.
+            </para>
+
+        </sect2>
+
+        <sect2 id="performance-cache-readonly">
+            <title>Strategie : lecture seule</title>
+
+            <para>
+                Si votre application a besoin de lire mais ne modifie jamais les instances d'une classe,
+        un cache <literal>read-only</literal> peut être utilisé. C'est la stratégie la plus simple
+        et la plus performante. Elle est même parfaitement sûre dans un cluster.
+            </para>
+
+            <programlisting><![CDATA[<class name="eg.Immutable" mutable="false">
+    <cache usage="read-only"/>
+    ....
+</class>]]></programlisting>
+
+        </sect2>
+
+
+        <sect2 id="performance-cache-readwrite">
+            <title>Stratégie : lecture/écriture</title>
+
+            <para>
+                Si l'application a besoin de mettre à jour des données, un cache <literal>read-write</literal> peut
+        être approprié. Cette stratégie ne devrait jamais être utilisée si votre application
+        nécessite un niveau d'isolation transactionnelle sérialisable. Si le cache est utilisé 
+        dans un environnement JTA, vous devez spécifier 
+        <literal>hibernate.transaction.manager_lookup_class</literal>, fournissant une stratégie pour obtenir
+        le <literal>TransactionManager</literal> JTA. Dans d'autres environnements, vous devriez vous assurer
+        que la transation est terminée à l'appel de <literal>Session.close()</literal> 
+        ou <literal>Session.disconnect()</literal>. Si vous souhaitez utiliser cette stratégie 
+        dans un cluster, vous devriez vous assurer que l'implémentation de cache utilisée supporte 
+        le vérrouillage. Ce que ne font <emphasis>pas</emphasis> les pourvoyeurs caches fournis.
+            </para>
+
+            <programlisting><![CDATA[<class name="eg.Cat" .... >
+    <cache usage="read-write"/>
+    ....
+    <set name="kittens" ... >
+        <cache usage="read-write"/>
+        ....
+    </set>
+</class>]]></programlisting>
+
+        </sect2>
+
+        <sect2 id="performance-cache-nonstrict">
+            <title>Stratégie : lecture/écriture non stricte</title>
+
+            <para>
+                Si l'application besoin de mettre à jour les données de manière occasionnelle 
+        (qu'il est très peu probable que deux transactions essaient de mettre à jour le même 
+        élément simultanément) et qu'une isolation transactionnelle stricte n'est pas nécessaire, 
+        un cache <literal>nonstrict-read-write</literal> peut être approprié. Si le cache est 
+        utilisé dans un environnement JTA, vous devez spécifier
+        <literal>hibernate.transaction.manager_lookup_class</literal>. Dans d'autres 
+        environnements, vous devriez vous assurer que la transation est terminée à l'appel 
+        de <literal>Session.close()</literal> ou <literal>Session.disconnect()</literal> 
+            </para>
+
+        </sect2>
+
+        <sect2 id="performance-cache-transactional">
+            <title>Stratégie : transactionelle</title>
+
+            <para>
+                La stratégie de cache <literal>transactional</literal> supporte un cache 
+        complètement transactionnel comme, par exemple, JBoss TreeCache. Un tel cache ne 
+        peut être utilisé que dans un environnement JTA et vous devez spécifier 
+        <literal>hibernate.transaction.manager_lookup_class</literal>. 
+            </para>
+
+        </sect2>
+        
+        <para>
+            Aucun des caches livrés ne supporte toutes les stratégies de concurrence. Le tableau suivant montre
+        quels caches sont compatibles avec quelles stratégies de concurrence.       
+        </para>
+
+        <table frame="topbot">
+            <title>Stratégie de concurrence du cache</title>
+            <tgroup cols='5' align='left' colsep='1' rowsep='1'>
+            <colspec colname='c1' colwidth="1*"/>
+            <colspec colname='c2' colwidth="1*"/>
+            <colspec colname='c3' colwidth="1*"/>
+            <colspec colname='c4' colwidth="1*"/>
+            <colspec colname='c5' colwidth="1*"/>
+            <thead>
+            <row>
+              <entry>Cache</entry>
+              <entry>read-only (lecture seule)</entry>
+              <entry>nonstrict-read-write (lecture-écriture non stricte)</entry>
+              <entry>read-write (lecture-ériture)</entry>
+              <entry>transactional (transactionnel)</entry>
+            </row>
+            </thead>
+            <tbody>
+            <row>
+                <entry>Hashtable (ne pas utilser en production)</entry>
+                <entry>oui</entry>
+                <entry>oui</entry>
+                <entry>oui</entry>
+                <entry></entry>
+            </row>
+            <row>
+                <entry>EHCache</entry>
+                <entry>oui</entry>
+                <entry>oui</entry>
+                <entry>oui</entry>
+                <entry></entry>
+            </row>
+            <row>
+                <entry>OSCache</entry>
+                <entry>oui</entry>
+                <entry>oui</entry>
+                <entry>oui</entry>
+                <entry></entry>
+            </row>
+            <row>
+                <entry>SwarmCache</entry>
+                <entry>oui</entry>
+                <entry>oui</entry>
+                <entry></entry>
+                <entry></entry>
+            </row>
+            <row>
+                <entry>JBoss TreeCache</entry>
+                <entry>oui</entry>
+                <entry></entry>
+                <entry></entry>
+                <entry>oui</entry>
+            </row>
+            </tbody>
+            </tgroup>
+        </table>
+
+    </sect1>
+
+    <sect1 id="performance-sessioncache" revision="2">
+        <title>Gérer les caches</title>
+
+        <para>
+            A chaque fois que vous passez un objet à la méthode <literal>save()</literal>, 
+            <literal>update()</literal> ou <literal>saveOrUpdate()</literal> et à chaque fois
+            que vous récupérez un objet avec <literal>load()</literal>, <literal>get()</literal>,
+            <literal>list()</literal>, <literal>iterate()</literal> or <literal>scroll()</literal>, 
+            cet objet est ajouté au cache interne de la <literal>Session</literal>. 
+        </para>
+        <para>
+            Lorsqu'il y a un appel à la méthode <literal>flush()</literal>, l'état de cet objet
+            va être synchronisé avec la base de données. Si vous ne voulez pas que cette synchronisation
+            ait lieu ou si vous traitez un grand nombre d'objets et que vous avez besoin de gérer
+            la mémoire de manière efficace, vous pouvez utiliser la méthode <literal>evict()</literal>
+            pour supprimer l'objet et ses collections dépendantes du cache de la session
+        </para>
+        
+        <programlisting><![CDATA[ScrollableResult cats = sess.createQuery("from Cat as cat").scroll(); //a huge result set
+while ( cats.next() ) {
+    Cat cat = (Cat) cats.get(0);
+    doSomethingWithACat(cat);
+    sess.evict(cat);
+}]]></programlisting>
+            
+        <para>
+          La <literal>Session</literal> dispose aussi de la méthode <literal>contains()</literal> pour déterminer
+            si une instance appartient au cache de la session.
+        </para>
+        
+        <para>
+            Pour retirer tous les objets du cache session, appelez <literal>Session.clear()</literal>
+        </para>
+        
+        <para>
+            Pour le cache de second niveau, il existe des méthodes définies dans 
+        <literal>SessionFactory</literal> pour retirer des instances du cache, 
+        la classe entière, une instance de collection ou
+        le rôle entier d'une collection.
+        </para>
+        
+        <programlisting><![CDATA[sessionFactory.evict(Cat.class, catId); //evict a particular Cat
+sessionFactory.evict(Cat.class);  //evict all Cats
+sessionFactory.evictCollection("Cat.kittens", catId); //evict a particular collection of kittens
+sessionFactory.evictCollection("Cat.kittens"); //evict all kitten collections]]></programlisting>
+
+        <para>
+            Le <literal>CacheMode</literal> contrôle comme une session particulière interragit avec le
+            cache de second niveau
+        </para>
+        
+        <itemizedlist>
+        <listitem>
+        <para>
+            <literal>CacheMode.NORMAL</literal> - lit et écrit les items dans le cache de second niveau
+        </para>
+        </listitem>
+        <listitem>
+        <para>
+            <literal>CacheMode.GET</literal> - lit les items dans le cache de second niveau mais ne
+            les écrit pas sauf dans le cache d'une mise à jour d'une donnée
+        </para>
+        </listitem>
+        <listitem>
+        <para>
+            <literal>CacheMode.PUT</literal> -  écrit les items dans le cache de second niveau mais ne les
+            lit pas dans le cache de second niveau
+        </para>
+        </listitem>
+        <listitem>
+        <para>
+            <literal>CacheMode.REFRESH</literal> - écrit les items dans le cache de second niveau mais ne les
+            lit pas dans le cache de second niveau, outrepasse l'effet de<literal>hibernate.cache.use_minimal_puts</literal>, 
+            en forçant un rafraîchissement du cache de second niveau pour chaque item lu dans la base
+        </para>
+        </listitem>
+        </itemizedlist>
+        
+        <para>
+            Pour parcourir le contenu du cache de second niveau ou la région du cache dédiée au requêtes, vous
+            pouvez utiliser l'API <literal>Statistics</literal>
+            API:
+        </para>
+        
+        <programlisting><![CDATA[Map cacheEntries = sessionFactory.getStatistics()
+        .getSecondLevelCacheStatistics(regionName)
+        .getEntries();]]></programlisting>
+        
+        <para>
+          Vous devez pour cela activer les statistiques et optionnellement forcer Hibernate à conserver les entrées dans le
+          cache sous un format plus compréhensible pour l'utilisateur :
+        </para>
+        
+        <programlisting><![CDATA[hibernate.generate_statistics true
+hibernate.cache.use_structured_entries true]]></programlisting>       
+                
+    </sect1>
+    
+    <sect1 id="performance-querycache" revision="1">
+        <title>Le cache de requêtes</title>
+
+        <para>
+          Les résultats d'une requête peuvent aussi être placés en cache. Ceci n'est utile
+            que pour les requêtes qui sont exécutées avec les mêmes paramètres. Pour utiliser
+            le cache de requêtes, vous devez d'abord l'activer :
+        </para>
+        
+        <programlisting><![CDATA[hibernate.cache.use_query_cache true]]></programlisting>       
+
+        <para>
+          Ce paramètre amène la création de deux nouvelles régions dans le cache, une qui va conserver
+          le résultat des requêtes mises en cache (<literal>org.hibernate.cache.StandardQueryCache</literal>)
+          et l'autre qui va conserver l'horodatage des mises à jour les plus récentes effectuées sur les
+          tables requêtables (<literal>org.hibernate.cache.UpdateTimestampsCache</literal>).
+          Il faut noter que le cache de requête ne conserve pas l'état des entités, il met en cache
+          uniquement les valeurs de l'identifiant et les valeurs de types de base (?). Le cache
+          de requête doit toujours être utilisé avec le cache de second niveau pour être efficace.
+        </para>
+        
+        <para>
+          La plupart des requêtes ne retirent pas de bénéfice pas du cache, 
+          donc par défaut les requêtes ne sont pas mises en cache. Pour activer le cache, 
+          appelez <literal>Query.setCacheable(true)</literal>. 
+            Cet appel permet de vérifier si les résultats sont en cache ou non, voire
+          d'ajouter ces résultats si la requête est exécutée.
+        </para>
+        
+        <para>
+          Si vous avez besoin de contrôler finement les délais d'expiration du cache, vous
+            pouvez spécifier une région de cache nommée pour une requête particulière en
+            appelant <literal>Query.setCacheRegion()</literal>.
+        </para>
+        
+        <programlisting><![CDATA[List blogs = sess.createQuery("from Blog blog where blog.blogger = :blogger")
+    .setEntity("blogger", blogger)
+    .setMaxResults(15)
+    .setCacheable(true)
+    .setCacheRegion("frontpages")
+    .list();]]></programlisting>
+    
+        <para>
+          Si une requête doit forcer le rafraîchissement de sa région de cache, vous devez
+          appeler <literal>Query.setCacheMode(CacheMode.REFRESH)</literal>. C'est particulièrement
+          utile lorsque les données peuvent avoir été mises à jour par un processus séparé (e.g. elles
+          n'ont pas été modifiées par Hibernate). Cela permet à l'application de rafraîchir de
+          manière sélective les résultats d'une requête particulière. Il s'agit d'une alternative plus
+          efficace à l'éviction d'une région du cache à l'aide de la méthode 
+          <literal>SessionFactory.evictQueries()</literal>.
+        </para>
+
+    </sect1>
+    <sect1 id="performance-collections">
+        <title>Comprendre les performances des Collections</title>
+
+        <para>
+            Nous avons déjà passé du temps à discuter des collections.
+        Dans cette section, nous allons traiter du comportement des
+        collections à l'exécution.
+        </para>
+
+        <sect2 id="performance-collections-taxonomy">
+            <title>Classification</title>
+
+            <para>Hibernate définit trois types de collections :</para>
+
+            <itemizedlist>
+            <listitem>
+                <para>les collections de valeurs</para>
+            </listitem>
+            <listitem>
+                <para>les associations un-vers-plusieurs</para>
+            </listitem>
+            <listitem>
+                <para>les associations plusieurs-vers-plusieurs</para>
+            </listitem>
+            </itemizedlist>
+
+            <para>
+                Cette classification distingue les différentes relations entre les tables
+        et les clés étrangères mais ne nous apprend rien de ce que nous devons savoir
+        sur le modèle relationnel. Pour comprendre parfaitement la structure relationnelle
+        et les caractéristiques des performances, nous devons considérer la structure
+        de la clé primaire qui est utilisée par Hibernate pour mettre à jour ou supprimer
+        les éléments des collections. Celà nous amène aux classifications suivantes :
+            </para>
+
+            <itemizedlist>
+            <listitem>
+                <para>collections indexées</para>
+            </listitem>
+            <listitem>
+                <para>sets</para>
+            </listitem>
+            <listitem>
+                <para>bags</para>
+            </listitem>
+            </itemizedlist>
+
+            <para>
+                Toutes les collections indexées (maps, lists, arrays) ont une clé primaire constituée 
+        des colonnes clé (<literal>&lt;key&gt;</literal>) et <literal>&lt;index&gt;</literal>.
+        Avec ce type de clé primaire, la mise à jour de collection est en général très performante - la clé
+        primaire peut être indexées efficacement et un élément particulier peut être 
+        localisé efficacement lorsqu'Hibernate essaie de le mettre à jour ou de le supprimer.
+            </para>
+
+            <para>
+              Les Sets ont une clé primaire composée de <literal>&lt;key&gt;</literal> et des
+              colonnes représentant l'élément. Elle est donc moins efficace pour certains 
+              types de collections d'éléments, en particulier les éléments composites, 
+              les textes volumineux ou les champs binaires ; la base de données
+                  peut ne pas être capable d'indexer aussi efficacement une clé primaire 
+              aussi complexe. Cependant, pour les associations un-vers-plusieurs 
+              ou plusieurs-vers-plusieurs, spécialement lorsque l'on utilise des entités
+              ayant des identifiants techniques, il est probable que cela soit aussi efficace
+                  (note : si vous voulez que <literal>SchemaExport</literal> créé effectivement
+              la clé primaire   d'un <literal>&lt;set&gt;</literal> pour vous, vous devez 
+              déclarer toutes les colonnes avec <literal>not-null="true"</literal>).
+            </para>
+
+            <para>
+              Le mapping à l'aide d'<literal>&lt;idbag&gt;</literal> définit une clé
+              de substitution ce qui leur permet d'être très efficaces lors de la
+              mise à jour. En fait il s'agit du meilleur cas de mise à jour d'une collection
+            </para>
+
+            <para>
+              Le pire cas intervient pour les Bags. Dans la mesure où un bag permet 
+              la duplications des éléments et n'a pas de colonne d'index, aucune clé primaire 
+              ne peut être définie. Hibernate   n'a aucun moyen de distinguer des enregistrements 
+              dupliqués. Hibernate résout ce problème en supprimant complètement les 
+              enregistrements (via un simple <literal>DELETE</literal>), puis en recréant
+                  la collection chaque fois qu'elle change. Ce qui peut être très inefficace.
+            </para>
+
+            <para>
+              Notez que pour une relation un-vers-plusieurs, la "clé primaire" 
+              peut ne pas être la clé   primaire de la table en base de données - 
+              mais même dans ce cas, la classification ci-dessus reste utile 
+              (Elle explique comment Hibernate "localise" chaque enregistrement
+                  de la collection).
+            </para>
+
+        </sect2>
+
+        <sect2 id="performance-collections-mostefficientupdate">
+            <title>Les lists, les maps, les idbags et les sets sont les collections les plus efficaces pour la mise à jour</title>
+
+            <para>
+              La discussion précédente montre clairement que les collections indexées 
+              et (la plupart du temps) les sets, permettent de réaliser le plus efficacement 
+              les opérations d'ajout, de suppression ou de modification d'éléments.     
+            </para>
+
+            <para>
+              Il existe un autre avantage qu'ont les collections indexées sur les Sets 
+                  dans le cadre d'une association plusieurs vers plusieurs ou d'une collection de valeurs.
+                  A cause de la structure inhérente d'un <literal>Set</literal>, Hibernate n'effectue jamais  
+                  d'<literal>UPDATE</literal> quand un enregistrement est modifié. Les modifications
+                  apportées à un <literal>Set</literal> se font via un <literal>INSERT</literal> et <literal>DELETE</literal> 
+                  (de chaque enregistrement). Une fois de plus, ce cas ne s'applique pas aux associations
+                un vers plusieurs.
+            </para>
+
+            <para>
+              Après s'être rappelé que les tableaux ne peuvent pas être chargés tardivement,
+              nous pouvons conclure que les lists, les maps et les idbags sont les types de collections
+              (non inversées) les plus performants, avec les sets pas loin derrières.
+              Les sets son le type de collection le plus courant dans les applications Hibernate. Cela
+              est du au fait que la sémantique des "set" est la plus naturelle dans le modèle
+              relationnel.
+            </para>
+
+            <para>
+                Cependant, dans des modèles objet bien conçus avec Hibernate, on voit souvent que
+                la plupart des collections sont en fait des associations "un-vers-plusieurs" avec
+                <literal>inverse="true"</literal>. Pour ces associations, les mises à jour sont gérées
+                au niveau de l'association "plusieurs-vers-un" et les considérations de performance de
+                mise à jour des collections ne s'appliquent tout simplement pas dans ces cas là.
+            </para>
+
+        </sect2>
+
+        <sect2 id="performance-collections-mostefficentinverse">
+            <title>Les Bags et les lists sont les plus efficaces pour les collections inverse</title>
+
+            <para>
+                Avant que vous n'oubliez les bags pour toujours, il y a un cas précis où les bags 
+        (et les lists) sont bien plus performants que les sets. Pour une collection marquée
+        comme <literal>inverse="true"</literal> (le choix le plus courant pour un relation
+        un vers plusieurs bidirectionnelle), nous pouvons ajouter des éléments à un bag 
+        ou une list sans avoir besoin de l'initialiser (fetch) les éléments du sac! 
+        Ceci parce que <literal>Collection.add()</literal> ou <literal>Collection.addAll()</literal> 
+        doit toujours retourner vrai pour un bag ou une <literal>List</literal>
+        (contrairement au <literal>Set</literal>). 
+        Cela peut rendre le code suivant beaucoup plus rapide.
+            </para>
+
+            <programlisting><![CDATA[Parent p = (Parent) sess.load(Parent.class, id);
+    Child c = new Child();
+    c.setParent(p);
+    p.getChildren().add(c);  //pas besoin de charger la collection !
+    sess.flush();]]></programlisting>
+
+        </sect2>
+
+        <sect2 id="performance-collections-oneshotdelete">
+            <title>Suppression en un coup</title>
+
+            <para>
+                Parfois, effacer les éléments d'une collection un par un peut être extrêmement inefficace.
+        Hibernate n'est pas totalement stupide, il sait qu'il ne faut pas le faire dans le cas d'une
+        collection complètement vidée (lorsque vous appellez <literal>list.clear()</literal>, par exemple).
+        Dans ce cas, Hibernate fera un simple <literal>DELETE</literal> et le travail est fait !
+            </para>
+
+            <para>
+                Supposons que nous ajoutions un élément dans une collection de taille vingt et que nous
+        enlevions ensuite deux éléments. Hibernate effectuera un <literal>INSERT</literal> puis
+        deux <literal>DELETE</literal> (à moins que la collection ne soit un bag). Ce qui est
+        souhaitable.
+            </para>
+
+            <para>
+                Cependant, supposons que nous enlevions dix huit éléments, laissant ainsi deux éléments, puis
+        que nous ajoutions trois nouveaux éléments. Il y a deux moyens de procéder.
+            </para>
+
+            <itemizedlist>
+            <listitem>
+                <para>effacer dix huit enregistrements un à un puis en insérer trois</para>
+            </listitem>
+            <listitem>
+                <para>effacer la totalité de la collection (en un <literal>DELETE</literal> SQL) puis insérer
+                les cinq éléments restant un à un</para>
+            </listitem>
+            </itemizedlist>
+
+            <para>
+                Hibernate n'est pas assez intelligent pour savoir que, dans ce cas, la seconde méthode est plus
+        rapide (Il plutôt heureux qu'Hibernate ne soit pas trop intelligent ; un tel comportement
+        pourrait rendre l'utilisation de triggers de bases de données plutôt aléatoire, etc...).
+            </para>
+
+            <para>
+                Heureusement, vous pouvez forcer ce comportement lorsque vous le souhaitez, en liberant 
+        (c'est-à-dire en déréférençant) la collection initiale et en retournant une collection
+        nouvellement instanciée avec les éléments restants. Ceci peut être très pratique et 
+        très puissant de temps en temps.
+            </para>
+
+            <para>
+              Bien sûr, la suppression en un coup ne s'applique pas pour les collections qui sont mappées
+              avec <literal>inverse="true"</literal>.
+            </para>
+        </sect2>
+
+    </sect1>
+
+    <sect1 id="performance-monitoring" revision="1">
+        <title>Moniteur de performance</title>
+
+        <para>
+          L'optimisation n'est pas d'un grand intérêt sans le suivi et l'accès aux données de
+          performance. Hibernate fournit toute une panoplie de rapport sur ses opérations internes.
+          Les statistiques dans Hibernate sont fournies par <literal>SessionFactory</literal>.
+        </para>
+
+        <sect2 id="performance-monitoring-sf" revision="2">
+            <title>Suivi d'une SessionFactory</title>
+
+            <para>
+              Vous pouvez accéder au métriques d'une <literal>SessionFactory</literal> de deux
+              manières. La première option est d'appeler <literal>sessionFactory.getStatistics()</literal>
+              et de lire ou d'afficher les <literal>Statistics</literal> vous même.
+            </para>
+
+            <para>
+              Hibernate peut également utiliser JMX pour publier les métriques si vous activez
+              le MBean <literal>StatisticsService</literal>. Vous pouvez activer un seul MBean
+              pour toutes vos <literal>SessionFactory</literal> ou un par factory. Voici un code
+              qui montre un exemple de configuration minimaliste :
+            </para>
+
+            <programlisting><![CDATA[// MBean service registration for a specific SessionFactory
+Hashtable tb = new Hashtable();
+tb.put("type", "statistics");
+tb.put("sessionFactory", "myFinancialApp");
+ObjectName on = new ObjectName("hibernate", tb); // MBean object name
+
+StatisticsService stats = new StatisticsService(); // MBean implementation
+stats.setSessionFactory(sessionFactory); // Bind the stats to a SessionFactory
+server.registerMBean(stats, on); // Register the Mbean on the server]]></programlisting>
+
+
+<programlisting><![CDATA[// MBean service registration for all SessionFactory's
+Hashtable tb = new Hashtable();
+tb.put("type", "statistics");
+tb.put("sessionFactory", "all");
+ObjectName on = new ObjectName("hibernate", tb); // MBean object name
+
+StatisticsService stats = new StatisticsService(); // MBean implementation
+server.registerMBean(stats, on); // Register the MBean on the server]]></programlisting>
+
+            <para>
+              TODO: Cela n'a pas de sens : dans le premier cs on récupère et on utilise le MBean directement.
+              Dans le second, on doit fournir le nom JNDI sous lequel est retenu la fabrique de session avant de
+              l'utiliser. Pour cela il faut utiliser
+                <literal>hibernateStatsBean.setSessionFactoryJNDIName("my/JNDI/Name")</literal>
+            </para>
+            <para>
+              Vous pouvez (dés)activer le suivi pour une <literal>SessionFactory</literal>
+            </para>
+            <itemizedlist>
+                <listitem>
+                    <para>
+                        au moment de la configuration en mettant <literal>hibernate.generate_statistics</literal> à <literal>false</literal>
+                    </para>
+                </listitem>
+            </itemizedlist>
+            <itemizedlist>
+                <listitem>
+                    <para>
+                        à chaud avec <literal>sf.getStatistics().setStatisticsEnabled(true)</literal>
+                        ou <literal>hibernateStatsBean.setStatisticsEnabled(true)</literal>
+                    </para>
+                </listitem>
+            </itemizedlist>
+
+            <para>
+              Les statistiques peuvent être remises à zéro de manière programmatique à l'aide de la méthode
+              <literal>clear()</literal>
+              Un résumé peut être envoyé à un logger (niveau info) à l'aide de la méthode <literal>logSummary()</literal>
+            </para>
+
+        </sect2>
+
+        <sect2 id="performance-monitoring-metrics" revision="1">
+            <title>Métriques</title>
+
+            <para>
+              Hibernate fournit un certain nombre de métriques, qui vont des informations très basiques
+              aux informations très spécialisées qui ne sont appropriées que dans certains scenarii.
+              Tous les compteurs accessibles sont décrits dans l'API de l'interface
+              <literal>Statistics</literal> dans trois catégories :
+            </para>
+            <itemizedlist>
+                <listitem>
+                    <para>
+                      Les métriques relatives à l'usage général de la <literal>Session</literal>
+                      comme le nombre de sessions ouvertes, le nombre de connexions JDBC récupérées, etc...
+                    </para>
+                </listitem>
+                <listitem>
+                    <para>
+                      Les métriques relatives aux entités, collections, requêtes et caches dans
+                      leur ensemble (métriques globales),
+                    </para>
+                </listitem>
+                <listitem>
+                    <para>
+                      Les métriques détaillées relatives à une entité, une collection, une requête
+                      ou une région de cache particulière.
+                    </para>
+                </listitem>
+            </itemizedlist>
+
+            <para>
+              Par exemple, vous pouvez vérifier l'accès au cache ainsi que le taux d'éléments manquants et
+              de mise à jour des entités, collections et requêtes et le temps moyen que met une requête.
+              Il faut faire attention au fait que le nombre de millisecondes est sujet à approximation en
+              Java. Hibernate est lié à la précision de la machine virtuelle, sur certaines plateformes,
+              cela n'offre qu'une précision de l'ordre de 10 secondes.
+            </para>
+
+            <para>
+              Des accesseurs simples sont utilisés pour accéder aux métriques globales (e.g. celles qui ne
+              sont pas liées à une entité, collection ou région de cache particulière). Vous pouvez accéder
+              aux métriques d'une entité, collection, région de cache particulière à l'aide de son nom et à l'aide
+              de sa représentation HQL ou SQL pour une requête. Référez vous à la javadoc des APIS 
+              <literal>Statistics</literal>, <literal>EntityStatistics</literal>,
+              <literal>CollectionStatistics</literal>, <literal>SecondLevelCacheStatistics</literal>,
+              and <literal>QueryStatistics</literal> pour plus d'informations. Le code ci-dessous montre
+              un exemple simple :
+            </para>
+
+            <programlisting><![CDATA[Statistics stats = HibernateUtil.sessionFactory.getStatistics();
+
+double queryCacheHitCount  = stats.getQueryCacheHitCount();
+double queryCacheMissCount = stats.getQueryCacheMissCount();
+double queryCacheHitRatio =
+  queryCacheHitCount / (queryCacheHitCount + queryCacheMissCount);
+
+log.info("Query Hit ratio:" + queryCacheHitRatio);
+
+EntityStatistics entityStats =
+  stats.getEntityStatistics( Cat.class.getName() );
+long changes =
+        entityStats.getInsertCount()
+        + entityStats.getUpdateCount()
+        + entityStats.getDeleteCount();
+log.info(Cat.class.getName() + " changed " + changes + "times"  );]]></programlisting>
+
+            <para>
+              Pour travailler sur toutes les entités, collections, requêtes et régions de cache, vous pouvez
+              récupérer la liste des noms des entités, collections, requêtes et régions de cache avec les
+              méthodes : <literal>getQueries()</literal>, <literal>getEntityNames()</literal>,
+                <literal>getCollectionRoleNames()</literal>, et
+                <literal>getSecondLevelCacheRegionNames()</literal>.
+            </para>
+
+        </sect2>
+
+    </sect1>
+
+</chapter>

Copied: core/trunk/documentation/manual/fr-FR/src/main/docbook/content/persistent_classes.xml (from rev 14070, core/trunk/documentation/manual/fr-FR/src/main/docbook/modules/persistent_classes.xml)
===================================================================
--- core/trunk/documentation/manual/fr-FR/src/main/docbook/content/persistent_classes.xml	                        (rev 0)
+++ core/trunk/documentation/manual/fr-FR/src/main/docbook/content/persistent_classes.xml	2007-10-09 18:28:36 UTC (rev 14074)
@@ -0,0 +1,536 @@
+<?xml version='1.0' encoding="iso-8859-1"?>
+<chapter id="persistent-classes" revision="2">
+    <title>Classes persistantes</title>
+
+    <para>
+        Les classes persistantes sont les classes d'une application qui implémentent
+        les entités d'un problème métier (ex. Client et Commande dans une application
+        de commerce électronique).
+        Toutes les instances d'une classe persistante ne sont pas forcément 
+        dans l'état persistant - au lieu de cela, une instance peut être éphémère (NdT : transient) ou détachée.
+    </para>
+
+    <para>
+        Hibernate fonctionne de manière optimale lorsque ces classes suivent quelques règles
+        simples, aussi connues comme le modèle de programmation Plain Old Java Object
+        (POJO). Cependant, aucune de ces règles ne sont des besoins absolus. En effet, Hibernate3 suppose très peu de choses à propos
+        de la nature de vos objets persistants. Vous pouvez exprimer un modèle de domaine par d'autres moyens : utiliser des arbres
+        d'instances de <literal>Map</literal>, par exemple.
+    </para>
+
+    <sect1 id="persistent-classes-pojo">
+        <title>Un exemple simple de POJO</title>
+
+        <para>
+            Toute bonne application Java nécessite une classe persistante
+            représentant les félins.
+        </para>
+
+        <programlisting><![CDATA[package eg;
+import java.util.Set;
+import java.util.Date;
+
+public class Cat {
+    private Long id; // identifier
+
+    private Date birthdate;
+    private Color color;
+    private char sex;
+    private float weight;
+    private int litterId;
+
+    private Cat mother;
+    private Set kittens = new HashSet();
+
+    private void setId(Long id) {
+        this.id=id;
+    }
+    public Long getId() {
+        return id;
+    }
+
+    void setBirthdate(Date date) {
+        birthdate = date;
+    }
+    public Date getBirthdate() {
+        return birthdate;
+    }
+
+    void setWeight(float weight) {
+        this.weight = weight;
+    }
+    public float getWeight() {
+        return weight;
+    }
+
+    public Color getColor() {
+        return color;
+    }
+    void setColor(Color color) {
+        this.color = color;
+    }
+
+    void setSex(char sex) {
+        this.sex=sex;
+    }
+    public char getSex() {
+        return sex;
+    }
+
+    void setLitterId(int id) {
+        this.litterId = id;
+    }
+    public int getLitterId() {
+        return litterId;
+    }
+
+    void setMother(Cat mother) {
+        this.mother = mother;
+    }
+    public Cat getMother() {
+        return mother;
+    }
+    void setKittens(Set kittens) {
+        this.kittens = kittens;
+    }
+    public Set getKittens() {
+        return kittens;
+    }
+
+    // addKitten not needed by Hibernate
+    public void addKitten(Cat kitten) {
+        kitten.setMother(this);
+    kitten.setLitterId( kittens.size() );
+        kittens.add(kitten);
+    }
+}]]></programlisting>
+
+        <para>
+            Il y a quatre règles à suivre ici :
+        </para>
+
+
+        <sect2 id="persistent-classes-pojo-constructor" revision="1">
+            <title>Implémenter un constructeur sans argument</title>
+
+            <para>
+                <literal>Cat</literal> a un constructeur sans argument. Toutes les classes persistantes doivent avoir un
+                constructeur par défaut (lequel peut ne pas être public) pour qu'Hibernate puissent les instancier en utilisant
+                <literal>Constructor.newInstance()</literal>. Nous recommandons fortement d'avoir un constructeur par défaut avec 
+                au moins une visibilité <emphasis>paquet</emphasis> pour la génération du proxy à l'exécution dans Hibernate.
+            </para>
+        </sect2>
+
+        <sect2 id="persistent-classes-pojo-identifier" revision="2">
+            <title>Fournir une propriété d'indentifiant (optionnel)</title>
+
+            <para>
+                <literal>Cat</literal> possède une propriété appelée <literal>id</literal>.
+                Cette propriété mappe la valeur de la colonne de clé primaire de la table
+                d'une base de données.La propriété aurait pu s'appeler complètement autrement,
+                et son type aurait pu être n'importe quel type primitif, n'importe quel "encapsuleur"
+                de type primitif, <literal>java.lang.String</literal> ou <literal>java.util.Date</literal>.
+                (Si votre base de données héritée possède des clés composites, elles peuvent être mappées
+                en utilisant une classe définie par l'utilisateur et possédant les propriétés associées aux
+                types de la clé composite - voir la section concernant les identifiants composites plus tard).
+            </para>
+
+            <para>
+                La propriété d'identifiant est strictement optionnelle. Vous pouver l'oublier et laisser Hibernate
+                s'occuper des identifiants de l'objet en interne. Toutefois, nous ne le recommandons pas.
+            </para>
+
+            <para>
+                En fait, quelques fonctionnalités ne sont disponibles que pour les classes
+                déclarant un identifiant de propriété :
+            </para>
+
+            <itemizedlist spacing="compact">
+                <listitem>
+                    <para>
+                        Les réattachements transitifs pour les objets détachés (mise à jour en cascade ou fusion en cascade) - 
+                        voir <xref linkend="objectstate-transitive"/>
+                    </para>
+                </listitem>
+                <listitem>
+                    <para>
+                        <literal>Session.saveOrUpdate()</literal>
+                    </para>
+                </listitem>
+                <listitem>
+                    <para>
+                        <literal>Session.merge()</literal>
+                    </para>
+                </listitem>
+            </itemizedlist>
+
+            <para>
+                Nous recommandons que vous déclariez les propriétés d'identifiant de manière
+                uniforme. Nous recommandons également que vous utilisiez un type nullable
+                (ie. non primitif).
+            </para>
+        </sect2>
+
+        <sect2 id="persistent-classes-pojo-final">
+            <title>Favoriser les classes non finales (optionnel)</title>
+            <para>
+                Une fonctionnalité clef d'Hibernate, les <emphasis>proxies</emphasis>, nécessitent
+                que la classe persistente soit non finale ou qu'elle soit l'implémentation d'une
+                interface qui déclare toutes les méthodes publiques.
+            </para>
+            <para>
+                Vous pouvez persister, grâce à Hibernate, les classes <literal>final</literal>
+                qui n'implémentent pas d'interface, mais vous ne pourrez pas utiliser les proxies pour les chargements d'associations paresseuses
+                - ce qui limitera vos possibilités d'ajustement des performances.
+            </para>
+            <para>
+                Vous devriez aussi éviter de déclarer des méthodes <literal>public final</literal> sur des classes
+                non-finales. Si vous voulez utiliser une classe avec une méthode <literal>public final</literal>, vous devez
+                explicitement désactiver les proxies en paramétrant
+                <literal>lazy="false"</literal>.
+            </para>
+        </sect2>
+
+        <sect2 id="persistent-classes-pojo-accessors" revision="2">
+            <title>Déclarer les accesseurs et mutateurs des attributs persistants (optionnel)</title>
+
+            <para>
+                <literal>Cat</literal> déclare des mutateurs pour toutes ses champs persistants. Beaucoup d'autres
+                solutions de mapping Objet/relationnel persistent directement les variables d'instance. Nous pensons
+                qu'il est bien mieux de fournir une indirection entre le schéma relationnel et les structures de données internes de la classe.
+                Par défaut, Hibernate persiste les propriétés suivant le style JavaBean, et reconnaît les noms de méthodes de la forme <literal>
+                getFoo</literal>, <literal>isFoo</literal> et
+                <literal>setFoo</literal>. Nous pouvons changer pour un accès direct aux champs pour des propriétés particulières, si besoin est.
+            </para>
+
+            <para>
+                Les propriétés <emphasis>n'ont pas</emphasis> à être déclarées publiques -
+                Hibernate peut persister une propriété avec un paire de getter/setter de
+                visibilité par défault, <literal>protected</literal> ou <literal>
+                private</literal>.
+            </para>
+
+        </sect2>
+
+    </sect1>
+
+    <sect1 id="persistent-classes-inheritance">
+        <title>Implémenter l'héritage</title>
+
+        <para>
+            Une sous-classe doit également suivre la première et la seconde règle.
+            Elle hérite sa propriété d'identifiant de <literal>Cat</literal>.
+        </para>
+
+        <programlisting><![CDATA[package eg;
+
+public class DomesticCat extends Cat {
+        private String name;
+
+        public String getName() {
+                return name;
+        }
+        protected void setName(String name) {
+                this.name=name;
+        }
+}]]></programlisting>
+    </sect1>
+
+    <sect1 id="persistent-classes-equalshashcode" revision="1">
+        <title>Implémenter <literal>equals()</literal> et <literal>hashCode()</literal></title>
+
+        <para>
+            Vous devez surcharger les méthodes <literal>equals()</literal> et
+            <literal>hashCode()</literal> si vous
+        </para>
+        <itemizedlist spacing="compact">
+            <listitem>
+                <para>
+                    avez l'intention de mettre des instances de classes persistantes dans un <literal>Set</literal>
+                    (la manière recommandée pour représenter des associations pluri-valuées)
+                    <emphasis>et</emphasis>
+                </para>
+            </listitem>
+            <listitem>
+                <para>
+                    avez l'intention d'utiliser le réattachement d'instances détachées
+                </para>
+            </listitem>
+        </itemizedlist>
+
+        <para>
+            Hibernate garantit l'équivalence de l'identité persistante (ligne de base de données) et l'identité Java seulement
+            à l'intérieur de la portée d'une session particulière. Donc dès que nous mélangeons des instances venant de différentes
+            sessions, nous devons implémenter <literal>equals()</literal> et
+            <literal>hashCode()</literal> si nous souhaitons avoir une sémantique correcte pour les <literal>Set</literal>s.
+        </para>
+
+        <para>
+            La manière la plus évidente est d'implémenter <literal>equals()</literal>/<literal>hashCode()</literal>
+            en comparant la valeur de l'identifiant des deux objets. Si cette valeur est identique, les deux
+            doivent représenter la même ligne de base de données, ils sont donc égaux (si les deux sont
+            ajoutés à un <literal>Set</literal>, nous n'aurons qu'un seul élément dans le
+            <literal>Set</literal>). Malheureusement, nous ne pouvons pas utiliser cette approche avec 
+            des identifiants générés ! Hibernate n'assignera de
+            valeur d'identifiant qu'aux objets qui sont persistants, une instance nouvellement créée n'aura
+            donc pas de valeur d'identifiant ! De plus, si une instance est non sauvegardée et actuellement dans un <literal>Set</literal>,
+            le sauvegarder assignera une valeur d'identifiant à l'objet. Si <literal>equals()</literal> et <literal>hashCode()</literal>
+            sont basées sur la valeur de l'identifiant, le code de hachage devrait changer, rompant le contrat du <literal>Set</literal>. 
+            Regardez sur le site web d'Hibernate pour une discussion complète de ce problème. 
+            Notez que ceci n'est pas un problème d'Hibernate, mais la sémantique normale de Java pour l'identité d'un objet et l'égalité.
+        </para>
+
+        <para>
+            Nous recommandons donc d'implémenter
+            <literal>equals()</literal> et <literal>hashCode()</literal> en utilisant <emphasis>
+            l'égalité par clé métier</emphasis>.L'égalité par clé métier signifie que la méthode <literal>equals()</literal>
+            compare uniquement les propriétés qui forment une clé métier, une clé qui
+            identifierait notre instance dans le monde réel (une clé candidate
+            <emphasis>naturelle</emphasis>) :
+        </para>
+
+        <programlisting><![CDATA[public class Cat {
+
+    ...
+    public boolean equals(Object other) {
+        if (this == other) return true;
+        if ( !(other instanceof Cat) ) return false;
+
+        final Cat cat = (Cat) other;
+
+        if ( !cat.getLitterId().equals( getLitterId() ) ) return false;
+        if ( !cat.getMother().equals( getMother() ) ) return false;
+
+        return true;
+    }
+
+    public int hashCode() {
+        int result;
+        result = getMother().hashCode();
+        result = 29 * result + getLitterId();
+        return result;
+    }
+
+}]]></programlisting>
+
+        <para>
+            Notez qu'une clef métier ne doit pas être solide comme une clef primaire de base de données 
+            (voir <xref linkend="transactions-basics-identity"/>). Les propriétés
+            immuables ou uniques sont généralement de bonnes candidates pour une clef métier.
+        </para>
+
+    </sect1>
+
+    <sect1 id="persistent-classes-dynamicmodels">
+        <title>Modèles dynamiques</title>
+
+        <para>
+            <emphasis>Notez que la fonctionnalités suivantes sont actuellement considérées
+            comme expérimentales et peuvent changer dans un futur proche.</emphasis>
+        </para>
+
+        <para>
+            Les entités persistantes ne doivent pas nécessairement être représentées comme
+            des classes POJO ou des objets JavaBean à l'exécution. Hibernate supporte aussi les
+            modèles dynamiques (en utilisant des <literal>Map</literal>s de <literal>Map</literal>s
+            à l'exécution) et la représentation des entités comme des arbres DOM4J. Avec cette
+            approche, vous n'écrivez pas de classes persistantes, seulement des fichiers de mapping.
+        </para>
+
+        <para>
+            Par défaut, Hibernate fonctionne en mode POJO normal. Vous pouvez paramétrer
+            un mode de représentation d'entité par défaut pour une <literal>SessionFactory</literal>
+            particulière en utilisant l'option de configuration <literal>default_entity_mode</literal>
+            (voir <xref linkend="configuration-optional-properties"/>).
+        </para>
+
+        <para>
+            Les exemples suivants démontrent la représentation utilisant des <literal>Map</literal>s.
+            D'abord, dans le fichier de mapping, un <literal>entity-name</literal> doit être déclaré
+            au lieu (ou en plus) d'un nom de classe :
+        </para>
+
+        <programlisting><![CDATA[<hibernate-mapping>
+
+    <class entity-name="Customer">
+
+        <id name="id"
+            type="long"
+            column="ID">
+            <generator class="sequence"/>
+        </id>
+
+        <property name="name"
+            column="NAME"
+            type="string"/>
+
+        <property name="address"
+            column="ADDRESS"
+            type="string"/>
+
+        <many-to-one name="organization"
+            column="ORGANIZATION_ID"
+            class="Organization"/>
+
+        <bag name="orders"
+            inverse="true"
+            lazy="false"
+            cascade="all">
+            <key column="CUSTOMER_ID"/>
+            <one-to-many class="Order"/>
+        </bag>
+
+    </class>
+
+</hibernate-mapping>]]></programlisting>
+
+        <para>
+            Notez que même si des associations sont déclarées en utilisant des noms de classe cible,
+            le type de cible d'une association peut aussi être une entité dynamique au lieu d'un POJO.
+        </para>
+
+        <para>
+            Après avoir configuré le mode d'entité par défaut à <literal>dynamic-map</literal>
+            pour la <literal>SessionFactory</literal>, nous pouvons lors de l'exécution fonctionner
+            avec des <literal>Map</literal>s de <literal>Map</literal>s :
+        </para>
+
+        <programlisting><![CDATA[Session s = openSession();
+Transaction tx = s.beginTransaction();
+Session s = openSession();
+
+// Create a customer
+Map david = new HashMap();
+david.put("name", "David");
+
+// Create an organization
+Map foobar = new HashMap();
+foobar.put("name", "Foobar Inc.");
+
+// Link both
+david.put("organization", foobar);
+
+// Save both
+s.save("Customer", david);
+s.save("Organization", foobar);
+
+tx.commit();
+s.close();]]></programlisting>
+
+        <para>
+            Les avantages d'un mapping dynamique sont un gain de temps pour le prototypage
+            sans la nécessité d'implémenter les classes d'entité. Pourtant, vous perdez la
+            vérification du typage au moment de la compilation et aurez plus d'exceptions à
+            gérer lors de l'exécution. Grâce au mapping d'Hibernate, le schéma de la base de
+            données peut facilement être normalisé et solidifié, permettant de rajouter une
+            implémentation propre du modèle de domaine plus tard.
+        </para>
+
+        <para>
+            Les modes de représentation d'une entité peut aussi être configuré par <literal>Session</literal> :
+        </para>
+
+        <programlisting><![CDATA[Session dynamicSession = pojoSession.getSession(EntityMode.MAP);
+
+// Create a customer
+Map david = new HashMap();
+david.put("name", "David");
+dynamicSession.save("Customer", david);
+...
+dynamicSession.flush();
+dynamicSession.close()
+...
+// Continue on pojoSession
+]]></programlisting>
+
+
+        <para>
+            Veuillez noter que l'appel à <literal>getSession()</literal> en utilisant un
+            <literal>EntityMode</literal> se fait sur l'API <literal>Session</literal>, pas
+            <literal>SessionFactory</literal>. De cette manière, la nouvelle <literal>Session</literal>
+            partage les connexions JDBC, transactions et autres informations de contexte sous-jacentes.
+            Cela signifie que vous n'avez pas à appeler <literal>flush()</literal> et <literal>close()</literal>
+            sur la <literal>Session</literal> secondaire, et laissez aussi la gestion de la transaction
+            et de la connexion à l'unité de travail primaire.
+        </para>
+
+        <para>
+            Plus d'informations à propos de la représentation XML peuvent être trouvées dans
+            <xref linkend="xml"/>.
+        </para>
+
+    </sect1>
+
+    <sect1 id="persistent-classes-tuplizers" revision="0">
+        <title>Tuplizers</title>
+
+        <para>
+            <literal>org.hibernate.tuple.Tuplizer</literal>, et ses sous-interfaces, sont responsables
+            de la gestion d'une représentation particulière d'un morceau de données, en fonction du
+            <literal>org.hibernate.EntityMode</literal> de réprésentation. Si un morceau donné de données
+            est pensé comme une structure de données, alors un tuplizer est la chose qui sait comment
+            créer une telle structure de données, comment extraire des valeurs et injecter des valeurs dans
+            une telle structure de données. Par exemple, pour le mode d'entité POJO, le tuplizer correspondant
+            sait comment créer le POJO à travers son constructeur et comment accéder aux propriétés du POJO
+            utilisant les accesseurs de la propriété définie. Il y a deux types de Tuplizers haut niveau,
+            représenté par les interfaces <literal>org.hibernate.tuple.EntityTuplizer</literal> et
+            <literal>org.hibernate.tuple.ComponentTuplizer</literal>. Les <literal>EntityTuplizer</literal>s
+            sont responsables de la gestion des contrats mentionnés ci-dessus pour les entités, alors que
+            les <literal>ComponentTuplizer</literal>s s'occupent des composants.
+        </para>
+
+        <para>
+            Les utilisateurs peuvent aussi brancher leurs propres tuplizers. Peut-être vous est-il nécessaire qu'une
+            implémentation de <literal>java.util.Map</literal> autre que <literal>java.util.HashMap</literal>
+            soit utilisée dans le mode d'entité dynamic-map ; ou peut-être avez-vous besoin de définir une
+            statégie de génération de proxy différente de celle utilisée par défaut. Les deux devraient être
+            effectuées en définissant une implémentation de tuplizer utilisateur. Les définitions de tuplizers
+            sont attachées au mapping de l'entité ou du composant qu'ils sont censés gérer. Retour à l'exemple de
+            notre entité utilisateur :
+        </para>
+
+        <programlisting><![CDATA[<hibernate-mapping>
+    <class entity-name="Customer">
+        <!--
+            Override the dynamic-map entity-mode
+            tuplizer for the customer entity
+        -->
+        <tuplizer entity-mode="dynamic-map"
+                class="CustomMapTuplizerImpl"/>
+
+        <id name="id" type="long" column="ID">
+            <generator class="sequence"/>
+        </id>
+
+        <!-- other properties -->
+        ...
+    </class>
+</hibernate-mapping>
+
+
+public class CustomMapTuplizerImpl
+        extends org.hibernate.tuple.DynamicMapEntityTuplizer {
+    // override the buildInstantiator() method to plug in our custom map...
+    protected final Instantiator buildInstantiator(
+            org.hibernate.mapping.PersistentClass mappingInfo) {
+        return new CustomMapInstantiator( mappingInfo );
+    }
+
+    private static final class CustomMapInstantiator
+            extends org.hibernate.tuple.DynamicMapInstantitor {
+        // override the generateMap() method to return our custom map...
+        protected final Map generateMap() {
+            return new CustomMap();
+        }
+    }
+}]]></programlisting>
+
+
+    </sect1>
+
+    <para>
+        TODO: Document user-extension framework in the property and proxy packages
+    </para>
+
+</chapter>
+

Added: core/trunk/documentation/manual/fr-FR/src/main/docbook/content/preface.xml
===================================================================
--- core/trunk/documentation/manual/fr-FR/src/main/docbook/content/preface.xml	                        (rev 0)
+++ core/trunk/documentation/manual/fr-FR/src/main/docbook/content/preface.xml	2007-10-09 18:28:36 UTC (rev 14074)
@@ -0,0 +1,112 @@
+<?xml version='1.0'?>
+
+<!DOCTYPE preface PUBLIC "-//OASIS//DTD DocBook XML V4.5//EN" "http://www.oasis-open.org/docbook/xml/4.5/docbookx.dtd">
+
+<preface id="preface">
+    <title>Préface</title>
+
+    <para>
+        Travailler dans les deux univers que sont l'orienté objet et la base de données
+        relationnelle peut être lourd et consommateur en temps dans le monde de
+        l'entreprise d'aujourd'hui. Hibernate est un outil de  mapping objet/relationnel
+        pour le monde Java. Le terme mapping objet/relationnel (ORM) décrit la technique
+        consistant à faire le lien entre la représentation objet des données
+        et sa représentation relationnelle basée sur un schéma SQL.
+    </para>
+
+    <para>
+        Non seulement, Hibernate s'occupe du transfert des classes Java dans les tables
+        de la base de données (et des types de données Java dans les types de données SQL),
+        mais il permet de requêter les données et propose des moyens de les récupérer.
+        Il peut donc réduire de manière significative le temps de développement qui
+        aurait été autrement perdu dans une manipulation manuelle des données via SQL
+        et JDBC.
+    </para>
+
+    <para>
+        Le but d'Hibernate est de libérer le développeur de 95 pourcent des tâches de
+        programmation liées à la persistance des données communes. Hibernate n'est
+        probablement pas la meilleure solution pour les applications centrées sur les
+        données qui n'utilisent que les procédures stockées pour implémenter la logique
+        métier dans la base de données, il est le plus utile dans les modèles métier orientés
+        objets dont la logique métier est implémentée dans la couche Java dite intermédiaire.
+        Cependant, Hibernate vous aidera à supprimer ou à encapsuler le code SQL
+        spécifique à votre base de données et vous aidera sur la tâche commune qu'est
+        la transformation des données d'une représentation tabulaire à une
+        représentation sous forme de graphe d'objets.
+    </para>
+
+    <para>
+        Si vous êtes nouveau dans Hibernate et le mapping Objet/Relationnel voire même en Java,
+        suivez ces quelques étapes :
+    </para>
+
+    <orderedlist>
+        <listitem>
+            <para>
+                Lisez <xref linkend="tutorial"/> pour un didacticiel plus long avec plus d'instructions étape par étape.
+            </para>
+        </listitem>
+        <listitem>
+            <para>
+                Lisez <xref linkend="architecture"/> pour comprendre les environnements dans lesquels
+                Hibernate peut être utilisé.
+            </para>
+        </listitem>
+        <listitem>
+            <para>
+                Regardez le répertoire <literal>eg</literal> de la distribution Hibernate, il contient
+                une application simple et autonome. Copiez votre pilote JDBC dans le répertoire
+                <literal>lib/</literal> et éditez <literal>src/hibernate.properties</literal>, en
+                positionnant correctement les valeurs pour votre base de données. A partir d'une
+                invite de commande dans le répertoire de la distribution, tapez <literal>ant eg</literal>
+                (cela utilise Ant), ou sous Windows tapez <literal>build eg</literal>.
+            </para>
+        </listitem>
+        <listitem>
+            <para>
+                Faîtes de cette documentation de référence votre principale source d'information.
+                Pensez à lire <emphasis>Java Persistence with Hibernate</emphasis>
+                (http://www.manning.com/bauer2) si vous avez besoin de plus d'aide avec le design
+                d'applications ou si vous préférez un tutoriel pas à pas. Visitez aussi
+                http://caveatemptor.hibernate.org et téléchargez l'application exemple
+                pour Java Persistence with Hibernate.
+            </para>
+        </listitem>
+        <listitem>
+            <para>
+                Les questions les plus fréquemment posées (FAQs) trouvent leur réponse sur le
+                site web Hibernate.
+            </para>
+        </listitem>
+        <listitem>
+            <para>
+                Des démos, exemples et tutoriaux de tierces personnes sont référencés sur
+                le site web Hibernate.
+            </para>
+        </listitem>
+        <listitem>
+            <para>
+                La zone communautaire (Community Area) du site web Hibernate est une
+                bonne source d'information sur les design patterns et sur différentes
+                solutions d'intégration d'Hibernate (Tomcat, JBoss, Spring Framework, Struts,
+                EJB, etc).
+            </para>
+        </listitem>
+     </orderedlist>
+
+     <para>
+         Si vous avez des questions, utilisez le forum utilisateurs du site web Hibernate.
+         Nous utilisons également l'outil de gestion des incidents JIRA pour tout ce qui
+         est rapports de bogue et demandes d'évolution. Si vous êtes intéressé par le
+         développement d'Hibernate, joignez-vous à la liste de diffusion de développement.
+     </para>
+
+     <para>
+         Le développement commercial, le support de production et les formations à Hibernate
+         sont proposés par JBoss Inc (voir http://www.hibernate.org/SupportTraining/). Hibernate
+         est un projet Open Source professionnel et un composant critique de la suite de produits
+         JBoss Enterprise Middleware System (JEMS).
+     </para>
+
+ </preface>

Copied: core/trunk/documentation/manual/fr-FR/src/main/docbook/content/query_criteria.xml (from rev 14070, core/trunk/documentation/manual/fr-FR/src/main/docbook/modules/query_criteria.xml)
===================================================================
--- core/trunk/documentation/manual/fr-FR/src/main/docbook/content/query_criteria.xml	                        (rev 0)
+++ core/trunk/documentation/manual/fr-FR/src/main/docbook/content/query_criteria.xml	2007-10-09 18:28:36 UTC (rev 14074)
@@ -0,0 +1,443 @@
+<?xml version="1.0" encoding="iso-8859-1"?>
+<chapter id="querycriteria">
+    <title>Requêtes par critères</title>
+
+    <para>
+        Hibernate offre une API d'interrogation par critères intuitive et extensible.
+    </para>
+
+    <sect1 id="querycriteria-creating">
+        <title>Créer une instance de <literal>Criteria</literal></title>
+
+        <para>
+            L'interface <literal>net.sf.hibernate.Criteria</literal> représente une requête sur une
+            classe persistente donnée. La <literal>Session</literal> fournit les instances de
+            <literal>Criteria</literal>.
+        </para>
+
+        <programlisting><![CDATA[Criteria crit = sess.createCriteria(Cat.class);
+crit.setMaxResults(50);
+List cats = crit.list();]]></programlisting>
+
+    </sect1>
+
+    <sect1 id="querycriteria-narrowing">
+        <title>Restriction du résultat</title>
+
+        <para>
+            Un criterion (critère de recherche) est une instance de l'interface
+            <literal>org.hibernate.criterion.Criterion</literal>. La classe
+            <literal>org.hibernate.criterion.Restrictions</literal> définit
+            des méthodes pour obtenir des types de <literal>Criterion</literal>
+            pré-définis.
+        </para>
+
+        <programlisting><![CDATA[List cats = sess.createCriteria(Cat.class)
+    .add( Restrictions.like("name", "Fritz%") )
+    .add( Restrictions.between("weight", minWeight, maxWeight) )
+    .list();]]></programlisting>
+
+        <para>
+            Les restrictions peuvent être goupées de manière logique.
+        </para>
+
+        <programlisting><![CDATA[List cats = sess.createCriteria(Cat.class)
+    .add( Restrictions.like("name", "Fritz%") )
+    .add( Restrictions.or(
+        Restrictions.eq( "age", new Integer(0) ),
+        Restrictions.isNull("age")
+    ) )
+    .list();]]></programlisting>
+
+       <programlisting><![CDATA[List cats = sess.createCriteria(Cat.class)
+    .add( Restrictions.in( "name", new String[] { "Fritz", "Izi", "Pk" } ) )
+    .add( Restrictions.disjunction()
+        .add( Restrictions.isNull("age") )
+        .add( Restrictions.eq("age", new Integer(0) ) )
+        .add( Restrictions.eq("age", new Integer(1) ) )
+        .add( Restrictions.eq("age", new Integer(2) ) )
+    ) )
+    .list();]]></programlisting>
+
+        <para>
+            Il y a plusieurs types de criterion pré-définis (sous classes de <literal>Restriction</literal>),
+            mais l'une d'entre elle particulièrement utile vous permet de spécifier directement
+        du SQL.
+        </para>
+
+        <programlisting><![CDATA[List cats = sess.createCriteria(Cat.class)
+    .add( Restrictions.sql("lower({alias}.name) like lower(?)", "Fritz%", Hibernate.STRING) )
+    .list();]]></programlisting>
+
+        <para>
+            La zone <literal>{alias}</literal> sera remplacée par l'alias de colonne de l'entité
+        que l'on souhaite intérroger.
+        </para>
+
+        <para>
+            Une autre approche pour obtenir un criterion est de le récupérer d'une instance de <literal>Property</literal>. 
+            Vous pouvez créer une <literal>Property</literal> en appelant <literal>Property.forName()</literal>.
+        </para>
+
+        <programlisting><![CDATA[
+Property age = Property.forName("age");
+List cats = sess.createCriteria(Cat.class)
+    .add( Restrictions.disjunction()
+        .add( age.isNull() )
+        .add( age.eq( new Integer(0) ) )
+        .add( age.eq( new Integer(1) ) )
+        .add( age.eq( new Integer(2) ) )
+    ) )
+    .add( Property.forName("name").in( new String[] { "Fritz", "Izi", "Pk" } ) )
+    .list();]]></programlisting>
+
+   </sect1>
+
+    <sect1 id="querycriteria-ordering">
+        <title>Trier les résultats</title>
+
+        <para>
+            Vous pouvez trier les résultats en utilisant <literal>org.hibernate.criterion.Order</literal>.
+        </para>
+
+        <programlisting><![CDATA[List cats = sess.createCriteria(Cat.class)
+    .add( Restrictions.like("name", "F%")
+    .addOrder( Order.asc("name") )
+    .addOrder( Order.desc("age") )
+    .setMaxResults(50)
+    .list();]]></programlisting>
+
+        <programlisting><![CDATA[List cats = sess.createCriteria(Cat.class)
+    .add( Property.forName("name").like("F%") )
+    .addOrder( Property.forName("name").asc() )
+    .addOrder( Property.forName("age").desc() )
+    .setMaxResults(50)
+    .list();]]></programlisting>
+
+    </sect1>
+
+    <sect1 id="querycriteria-associations" revision="2">
+        <title>Associations</title>
+
+        <para>
+            Vous pouvez facilement spécifier des contraintes sur des entités liées,
+        par des associations en utilisant <literal>createCriteria()</literal>.
+        </para>
+
+        <programlisting><![CDATA[List cats = sess.createCriteria(Cat.class)
+    .add( Restrictions.like("name", "F%")
+    .createCriteria("kittens")
+        .add( Restrictions.like("name", "F%")
+    .list();]]></programlisting>
+
+        <para>
+            Notez que la seconde <literal>createCriteria()</literal> retourne une nouvelle
+            instance de <literal>Criteria</literal>, qui se rapporte aux éléments de la
+        collection <literal>kittens</literal>.
+        </para>
+
+        <para>
+            La forme alternative suivante est utile dans certains cas.
+        </para>
+
+        <programlisting><![CDATA[List cats = sess.createCriteria(Cat.class)
+    .createAlias("kittens", "kt")
+    .createAlias("mate", "mt")
+    .add( Restrictions.eqProperty("kt.name", "mt.name") )
+    .list();]]></programlisting>
+
+        <para>
+            (<literal>createAlias()</literal> ne crée pas de nouvelle instance de
+            <literal>Criteria</literal>.)
+        </para>
+
+        <para>
+            Notez que les collections kittens contenues dans les instances de <literal>Cat</literal>
+            retournées par les deux précédentes requêtes ne sont <emphasis>pas</emphasis> pré-filtrées
+            par les critères ! Si vous souhaitez récupérer uniquement les kittens qui correspondent à la
+            criteria, vous devez utiliser <literal>ResultTransformer</literal>.
+        </para>
+
+        <programlisting><![CDATA[List cats = sess.createCriteria(Cat.class)
+    .createCriteria("kittens", "kt")
+        .add( Restrictions.eq("name", "F%") )
+    .setResultTransformer(Criteria.ALIAS_TO_ENTITY_MAP)
+    .list();
+Iterator iter = cats.iterator();
+while ( iter.hasNext() ) {
+    Map map = (Map) iter.next();
+    Cat cat = (Cat) map.get(Criteria.ROOT_ALIAS);
+    Cat kitten = (Cat) map.get("kt");
+}]]></programlisting>
+
+    </sect1>
+
+    <sect1 id="querycriteria-dynamicfetching" revision="1">
+        <title>Peuplement d'associations de manière dynamique</title>
+
+        <para>
+            Vous pouvez spéficier au moment de l'exécution le peuplement d'une association en utilisant
+            <literal>setFetchMode()</literal> (c'est-à-dire le chargement de celle-ci).
+            Cela permet de surcharger les valeurs
+            "lazy" et "outer-join" du mapping.
+        </para>
+
+        <programlisting><![CDATA[List cats = sess.createCriteria(Cat.class)
+    .add( Restrictions.like("name", "Fritz%") )
+    .setFetchMode("mate", FetchMode.EAGER)
+    .setFetchMode("kittens", FetchMode.EAGER)
+    .list();]]></programlisting>
+
+        <para>
+            Cette requête recherchera <literal>mate</literal> et <literal>kittens</literal>
+            via les jointures externes. Voir <xref linkend="performance-fetching"/> pour plus d'informations.
+        </para>
+
+    </sect1>
+
+    <sect1 id="querycriteria-examples">
+        <title>Requêtes par l'exemple</title>
+
+        <para>
+            La classe <literal>org.hibernate.criterion.Example</literal> vous permet de
+            construire un critère suivant une instance d'objet donnée.
+        </para>
+
+        <programlisting><![CDATA[Cat cat = new Cat();
+cat.setSex('F');
+cat.setColor(Color.BLACK);
+List results = session.createCriteria(Cat.class)
+    .add( Example.create(cat) )
+    .list();]]></programlisting>
+
+        <para>
+            Les propriétés de type version, identifiant et association sont ignorées.
+       Par défaut, les valeurs null sont exclues.
+        </para>
+
+        <para>
+            Vous pouvez ajuster la stratégie d'utilisation de valeurs de
+           l'<literal>Exemple</literal>.
+        </para>
+
+        <programlisting><![CDATA[Example example = Example.create(cat)
+    .excludeZeroes()           //exclude zero valued properties
+    .excludeProperty("color")  //exclude the property named "color"
+    .ignoreCase()              //perform case insensitive string comparisons
+    .enableLike();             //use like for string comparisons
+List results = session.createCriteria(Cat.class)
+    .add(example)
+    .list();]]></programlisting>
+
+        <para>
+            Vous pouvez utiliser les "exemples" pour des critères sur les objets associés.
+        </para>
+
+        <programlisting><![CDATA[List results = session.createCriteria(Cat.class)
+    .add( Example.create(cat) )
+    .createCriteria("mate")
+        .add( Example.create( cat.getMate() ) )
+    .list();]]></programlisting>
+
+    </sect1>
+
+    <sect1 id="querycriteria-projection">
+        <title>Projections, agrégation et regroupement</title>
+        <para>
+            La classe <literal>org.hibernate.criterion.Projections</literal> est une
+            fabrique d'instances de <literal>Projection</literal>. Nous appliquons une
+            projection sur une requête en appelant <literal>setProjection()</literal>.
+        </para>
+
+        <programlisting><![CDATA[List results = session.createCriteria(Cat.class)
+    .setProjection( Projections.rowCount() )
+    .add( Restrictions.eq("color", Color.BLACK) )
+    .list();]]></programlisting>
+
+        <programlisting><![CDATA[List results = session.createCriteria(Cat.class)
+    .setProjection( Projections.projectionList()
+        .add( Projections.rowCount() )
+        .add( Projections.avg("weight") )
+        .add( Projections.max("weight") )
+        .add( Projections.groupProperty("color") )
+    )
+    .list();]]></programlisting>
+
+        <para>
+            Il n'y a pas besoin de "group by" explicite dans une requête par critère.
+            Certains types de projection sont définis pour être des <emphasis>projections
+            de regroupement</emphasis>, lesquels apparaissent aussi dans la clause
+            <literal>group by</literal> SQL.
+        </para>
+
+        <para>
+            Un alias peut optionnellement être assigné à une projection, ainsi la valeur
+            projetée peut être référencée dans des restrictions ou des tris. Voici deux façons
+            différentes de faire ça :
+        </para>
+
+        <programlisting><![CDATA[List results = session.createCriteria(Cat.class)
+    .setProjection( Projections.alias( Projections.groupProperty("color"), "colr" ) )
+    .addOrder( Order.asc("colr") )
+    .list();]]></programlisting>
+
+        <programlisting><![CDATA[List results = session.createCriteria(Cat.class)
+    .setProjection( Projections.groupProperty("color").as("colr") )
+    .addOrder( Order.asc("colr") )
+    .list();]]></programlisting>
+
+        <para>
+            Les méthodes <literal>alias()</literal> et <literal>as()</literal> enveloppe simplement
+            une instance de projection dans une autre instance (aliasée) de <literal>Projection</literal>.
+            Comme un raccourci, vous pouvez assignez un alias lorsque vous ajoutez la projection à la
+            liste de projections :
+        </para>
+
+       <programlisting><![CDATA[List results = session.createCriteria(Cat.class)
+    .setProjection( Projections.projectionList()
+        .add( Projections.rowCount(), "catCountByColor" )
+        .add( Projections.avg("weight"), "avgWeight" )
+        .add( Projections.max("weight"), "maxWeight" )
+        .add( Projections.groupProperty("color"), "color" )
+    )
+    .addOrder( Order.desc("catCountByColor") )
+    .addOrder( Order.desc("avgWeight") )
+    .list();]]></programlisting>
+
+        <programlisting><![CDATA[List results = session.createCriteria(Domestic.class, "cat")
+    .createAlias("kittens", "kit")
+    .setProjection( Projections.projectionList()
+        .add( Projections.property("cat.name"), "catName" )
+        .add( Projections.property("kit.name"), "kitName" )
+    )
+    .addOrder( Order.asc("catName") )
+    .addOrder( Order.asc("kitName") )
+    .list();]]></programlisting>
+
+        <para>
+            Vous pouvez aussi utiliser <literal>Property.forName()</literal> pour formuler des projections :
+        </para>
+
+        <programlisting><![CDATA[List results = session.createCriteria(Cat.class)
+    .setProjection( Property.forName("name") )
+    .add( Property.forName("color").eq(Color.BLACK) )
+    .list();]]></programlisting>
+
+        <programlisting><![CDATA[List results = session.createCriteria(Cat.class)
+    .setProjection( Projections.projectionList()
+        .add( Projections.rowCount().as("catCountByColor") )
+        .add( Property.forName("weight").avg().as("avgWeight") )
+        .add( Property.forName("weight").max().as("maxWeight") )
+        .add( Property.forName("color").group().as("color" )
+    )
+    .addOrder( Order.desc("catCountByColor") )
+    .addOrder( Order.desc("avgWeight") )
+    .list();]]></programlisting>
+
+    </sect1>
+
+    <sect1 id="querycriteria-detachedqueries">
+        <title>Requêtes et sous-requêtes détachées</title>
+        <para>
+            La classe <literal>DetachedCriteria</literal> vous laisse créer une requête en dehors de la
+            portée de la session, et puis l'exécuter plus tard en utilisant n'importe quelle <literal>Session</literal>
+            arbitraire.
+        </para>
+
+        <programlisting><![CDATA[DetachedCriteria query = DetachedCriteria.forClass(Cat.class)
+    .add( Property.forName("sex").eq('F') );
+
+Session session = ....;
+Transaction txn = session.beginTransaction();
+List results = query.getExecutableCriteria(session).setMaxResults(100).list();
+txn.commit();
+session.close();]]></programlisting>
+
+        <para>
+            Une <literal>DetachedCriteria</literal> peut aussi être utilisée pour exprimer une
+            sous-requête. Des instances de criterion impliquant des sous-requêtes peuvent être
+            obtenues via <literal>Subqueries</literal> ou <literal>Property</literal>.
+        </para>
+
+        <programlisting><![CDATA[DetachedCriteria avgWeight = DetachedCriteria.forClass(Cat.class)
+    .setProjection( Property.forName("weight").avg() );
+session.createCriteria(Cat.class)
+    .add( Property.forName("weight").gt(avgWeight) )
+    .list();]]></programlisting>
+
+        <programlisting><![CDATA[DetachedCriteria weights = DetachedCriteria.forClass(Cat.class)
+    .setProjection( Property.forName("weight") );
+session.createCriteria(Cat.class)
+    .add( Subqueries.geAll("weight", weights) )
+    .list();]]></programlisting>
+
+        <para>
+            Même des requêtes corrélées sont possibles :
+        </para>
+
+        <programlisting><![CDATA[DetachedCriteria avgWeightForSex = DetachedCriteria.forClass(Cat.class, "cat2")
+    .setProjection( Property.forName("weight").avg() )
+    .add( Property.forName("cat2.sex").eqProperty("cat.sex") );
+session.createCriteria(Cat.class, "cat")
+    .add( Property.forName("weight").gt(avgWeightForSex) )
+    .list();]]></programlisting>
+
+    </sect1>
+
+        <!--TODO: ResultSetTransformer + aliasing. AliasToBeanTransformer allow returning arbitrary
+                  user objects - similar to setResultClass in JDO2. General use of ResultTransformer
+                  could also be explained. -->
+
+    <sect1 id="query-criteria-naturalid">
+        <title>Requêtes par identifiant naturel</title>
+
+        <para>
+            Pour la plupart des requêtes, incluant les requêtes par critère, le cache de requêtes
+            n'est pas très efficace, parce que l'invalidation du cache de requêtes arrive trop
+            souvent. Cependant, il y a une sorte spéciale de requête où nous pouvons optimiser
+            l'algorithme d'invalidation du cache : les recherches sur une clef naturelle constante.
+            Dans certaines applications, cette sorte de requête se produit fréquemment. L'API de
+            critère fournit une provision spéciale pour ce cas d'utilisation.
+        </para>
+
+        <para>
+            D'abord vous devriez mapper la clef naturelle de votre entité en utilisant
+            <literal>&lt;natural-id&gt;</literal>, et activer l'utilisation du cache de second niveau.
+        </para>
+
+        <programlisting><![CDATA[<class name="User">
+    <cache usage="read-write"/>
+    <id name="id">
+        <generator class="increment"/>
+    </id>
+    <natural-id>
+        <property name="name"/>
+        <property name="org"/>
+    </natural-id>
+    <property name="password"/>
+</class>]]></programlisting>
+
+        <para>
+            Notez que cette fonctionnalité n'est pas prévue pour l'utilisation avec des
+            entités avec des clefs naturelles <emphasis>mutables</emphasis>.
+        </para>
+
+        <para>
+            Ensuite, activez le cache de requête d'Hibernate.
+        </para>
+
+        <para>
+            Maintenant <literal>Restrictions.naturalId()</literal> nous permet de rendre
+            l'utilisation de l'algorithme de cache plus efficace.
+        </para>
+
+        <programlisting><![CDATA[session.createCriteria(User.class)
+    .add( Restrictions.naturalId()
+        .set("name", "gavin")
+        .set("org", "hb")
+    ).setCacheable(true)
+    .uniqueResult();]]></programlisting>
+
+    </sect1>
+
+</chapter>

Copied: core/trunk/documentation/manual/fr-FR/src/main/docbook/content/query_hql.xml (from rev 14070, core/trunk/documentation/manual/fr-FR/src/main/docbook/modules/query_hql.xml)
===================================================================
--- core/trunk/documentation/manual/fr-FR/src/main/docbook/content/query_hql.xml	                        (rev 0)
+++ core/trunk/documentation/manual/fr-FR/src/main/docbook/content/query_hql.xml	2007-10-09 18:28:36 UTC (rev 14074)
@@ -0,0 +1,1149 @@
+<?xml version="1.0" encoding="iso-8859-1"?>
+<chapter id="queryhql">
+    <title>HQL: Langage de requêtage d'Hibernate</title>
+
+    <para>
+        Hibernate fourni un langage d'interrogation extrêmement puissant qui
+        ressemble (et c'est voulu) au SQL. Mais ne soyez pas distraits par la syntaxe ;
+        HQL est totalement orienté objet, comprenant des notions d'héritage, de
+        polymorphisme et d'association.
+    </para>
+
+    <sect1 id="queryhql-casesensitivity">
+        <title>Sensibilité à la casse</title>
+
+        <para>
+            Les requêtes sont insensibles à la casse, à l'exception des noms des classes Java
+            et des propriétés.
+            Ainsi, <literal>SeLeCT</literal> est identique à
+            <literal>sELEct</literal> et à
+            <literal>SELECT</literal> mais
+            <literal>net.sf.hibernate.eg.FOO</literal> n'est pas identique
+            <literal>net.sf.hibernate.eg.Foo</literal> et
+            <literal>foo.barSet</literal> n'est pas identique à
+            <literal>foo.BARSET</literal>.
+        </para>
+
+        <para>
+            Ce guide utilise les mots clés HQL en minuscule. Certains utilisateurs trouvent les
+            requêtes écrites avec les mots clés en majuscule plus lisibles, mais nous trouvons
+            cette convention pénible lorsqu'elle est lue dans du code Java.
+        </para>
+
+    </sect1>
+
+    <sect1 id="queryhql-from">
+        <title>La clause from</title>
+
+        <para>
+            La requête Hibernate la plus simple est de la forme :
+        </para>
+
+        <programlisting><![CDATA[from eg.Cat]]></programlisting>
+
+        <para>
+            qui retourne simplement toutes les instances de la classe <literal>eg.Cat</literal>. 
+            Nous n'avons pas besoin d'habitude de qualifier le nom de la classe, 
+            puisque <literal>auto-import</literal> est la valeur par défaut. Donc nous écrivons presque toujours :
+        </para>
+
+        <programlisting><![CDATA[from Cat]]></programlisting>
+
+        <para>
+            La plupart du temps, vous devrez assigner un <emphasis>alias</emphasis> puisque vous
+            voudrez faire référence à <literal>Cat</literal> dans d'autres parties de la requête.
+        </para>
+
+        <programlisting><![CDATA[from Cat as cat]]></programlisting>
+
+        <para>
+            Cette requête assigne l'alias <literal>cat</literal> à l'instance <literal>Cat</literal>,
+            nous pouvons donc utiliser cet alias ailleurs dans la requête. Le mot clé <literal>as</literal>
+            est optionnel ; nous aurions pu écrire :
+        </para>
+
+        <programlisting><![CDATA[from Cat cat]]></programlisting>
+
+        <para>
+            Plusieurs classes peuvent apparaître, ce qui conduira à un produit
+            cartésien (encore appelé jointures croisées).
+        </para>
+
+        <programlisting><![CDATA[from Formula, Parameter]]></programlisting>
+        <programlisting><![CDATA[from Formula as form, Parameter as param]]></programlisting>
+
+        <para>
+            C'est une bonne pratique que de nommer les alias dans les requêtes en utilisant l'initiale
+            en miniscule, ce qui a le mérite d'être en phase avec les standards de
+            nommage Java pour les variables locales (<literal>domesticCat</literal>).
+        </para>
+
+    </sect1>
+
+    <sect1 id="queryhql-joins" revision="1">
+        <title>Associations et jointures</title>
+
+        <para>
+            On peut aussi assigner des alias à des entités associées, ou même aux éléments d'une collection
+            de valeurs, en utilisant un <literal>join</literal> (jointure).
+        </para>
+
+        <programlisting><![CDATA[from Cat as cat
+    inner join cat.mate as mate
+    left outer join cat.kittens as kitten]]></programlisting>
+
+        <programlisting><![CDATA[from Cat as cat left join cat.mate.kittens as kittens]]></programlisting>
+
+        <programlisting><![CDATA[from Formula form full join form.parameter param]]></programlisting>
+
+        <para>
+            Les types de jointures supportées sont celles de ANSI SQL
+        </para>
+
+        <itemizedlist spacing="compact">
+            <listitem>
+                <para>
+                    <literal>inner join</literal> (jointure fermée)
+                </para>
+            </listitem>
+            <listitem>
+                <para>
+                    <literal>left outer join</literal> (jointure ouverte par la gauche)
+                </para>
+            </listitem>
+            <listitem>
+                <para>
+                    <literal>right outer join</literal> (jointure ouverte par la droite)
+                </para>
+            </listitem>
+            <listitem>
+                <para>
+                    <literal>full join</literal> (jointure ouverte totalement - généralement inutile)
+                </para>
+            </listitem>
+        </itemizedlist>
+
+        <para>
+            Les constructions des jointures <literal>inner join</literal>, <literal>left outer join</literal>
+            et <literal>right outer join</literal> peuvent être abbrégées.
+        </para>
+
+        <programlisting><![CDATA[from Cat as cat
+    join cat.mate as mate
+    left join cat.kittens as kitten]]></programlisting>
+
+        <para>
+            Nous pouvons soumettre des conditions de jointure supplémentaires en utilisant le mot-clef HQL <literal>with</literal>.
+        </para>
+
+        <programlisting><![CDATA[from Cat as cat
+    left join cat.kittens as kitten
+        with kitten.bodyWeight > 10.0]]></programlisting>
+
+        <para>
+            Par ailleurs, une jointure "fetchée" (rapportée) permet d'initialiser
+            les associations ou collections de valeurs en même temps que leur objet parent,
+            le tout n'utilisant qu'un seul Select.
+            Ceci est particulièrement utile dans le cas des collections. Ce système permet de surcharger
+            les déclarations "lazy" et "outer-join" des fichiers de mapping pour les associations et
+            collections. Voir
+            <xref linkend="performance-fetching"/> pour plus d'informations.
+        </para>
+
+        <programlisting><![CDATA[from Cat as cat
+    inner join fetch cat.mate
+    left join fetch cat.kittens]]></programlisting>
+
+        <para>
+            Une jointure "fetchée" (rapportée) n'a généralement pas besoin de se voir assigner
+            un alias puisque les objets associés n'ont pas à être utilisés dans les autres clauses.
+            Notez aussi que les objets associés ne sont pas retournés directement dans le résultat de
+            la requête mais l'on peut y accéder via l'objet parent. La seule raison pour laquelle nous 
+            pourrions avoir besoin d'un alias est si nous récupérions récursivement une collection supplémentaire :
+        </para>
+
+        <programlisting><![CDATA[from Cat as cat
+    inner join fetch cat.mate
+    left join fetch cat.kittens child
+    left join fetch child.kittens]]></programlisting>
+
+        <para>
+            Notez que la construction de <literal>fetch</literal> ne peut pas être utilisée dans les requêtes appelées par
+            <literal>scroll()</literal> ou <literal>iterate()</literal>.
+            <literal>fetch</literal> ne devrait pas non plus être utilisé avec <literal>setMaxResults()</literal> ou
+            <literal>setFirstResult()</literal>. <literal>fetch</literal> ne peut pas non plus être utilisé avec une 
+            condition <literal>with</literal> ad hoc. Il est
+            possible de créer un produit cartésien par jointure en récupérant plus d'une collection dans une requête, 
+            donc faites attention dans ce cas. Récupérer par jointure de multiples collections donne aussi parfois 
+            des résultats inattendus pour des mappings de bag, donc soyez prudent lorsque vous formulez vos requêtes dans de tels cas.
+            Finalement, notez que <literal>full join fetch</literal> et <literal>right join fetch</literal> ne sont pas utiles en général.
+        </para>
+
+        <para>
+            Si vous utilisez un chargement retardé pour les propriétés (avec une instrumentation par bytecode), il est possible 
+            de forcer Hibernate à récupérer les propriétés non encore chargées immédiatement (dans la première requête) 
+            en utilisant <literal>fetch all properties</literal>.
+        </para>
+
+        <programlisting><![CDATA[from Document fetch all properties order by name]]></programlisting>
+        <programlisting><![CDATA[from Document doc fetch all properties where lower(doc.name) like '%cats%']]></programlisting>
+
+    </sect1>
+    
+        <sect1 id="queryhql-joins-forms">
+        <title>Formes de syntaxes pour les jointures</title>
+
+        <para>
+            HQL supporte deux formes pour joindre les associations: <literal>implicite</literal> et <literal>explicite</literal>.
+        </para>
+
+        <para>
+            Les requêtes présentes dans la section précédente utilisent la forme <literal>explicite</literal> 
+            où le mode clé join est explicitement utilisé dans la clause from. C'est la forme recommandée.
+        </para>
+
+        <para>
+            La forme <literal>implicite</literal> n'utilise pas le mot clé join.
+            A la place, les associations sont "déréférencées" en utilisant le notation '.'. Ces
+            jointures peuvent apparaitre dans toutes les clauses. Les jointures <literal>implicites</literal> 
+            résultent en des inner join dans le SQL généré.
+        </para>
+
+        <programlisting><![CDATA[from Cat as cat where cat.mate.name like '%s%']]></programlisting>
+    </sect1>
+
+    <sect1 id="queryhql-select">
+        <title>La clause select</title>
+
+        <para>
+            La clause <literal>select</literal> sélectionne les objets et propriétés
+            qui doivent être retournés dans le résultat de la requête.
+        Soit :
+        </para>
+
+        <programlisting><![CDATA[select mate
+from Cat as cat
+    inner join cat.mate as mate]]></programlisting>
+
+        <para>
+            La requête recherchera les <literal>mate</literal>s liés aux <literal>Cat</literal>s.
+            Vous pouvez explimer la requête d'une manière plus compacte :
+        </para>
+
+        <programlisting><![CDATA[select cat.mate from Cat cat]]></programlisting>
+
+        <para>
+            Les requêtes peuvent retourner des propriétés de n'importe quel type, même celles de type
+        composant (component) :
+        </para>
+
+        <programlisting><![CDATA[select cat.name from DomesticCat cat
+where cat.name like 'fri%']]></programlisting>
+
+        <programlisting><![CDATA[select cust.name.firstName from Customer as cust]]></programlisting>
+
+        <para>
+            Les requêtes peuvent retourner plusieurs objets et/ou propriétés sous la forme
+        d'un tableau du type <literal>Object[]</literal>,
+        </para>
+
+        <programlisting><![CDATA[select mother, offspr, mate.name
+from DomesticCat as mother
+    inner join mother.mate as mate
+    left outer join mother.kittens as offspr]]></programlisting>
+
+        <para>
+            ou sous la forme d'une <literal>List</literal>,
+        </para>
+
+        <programlisting><![CDATA[select new list(mother, offspr, mate.name)
+from DomesticCat as mother
+    inner join mother.mate as mate
+    left outer join mother.kittens as offspr]]></programlisting>
+
+        <para>
+            ou sous la forme d'un objet Java typé,
+        </para>
+
+        <programlisting><![CDATA[select new Family(mother, mate, offspr)
+from DomesticCat as mother
+    join mother.mate as mate
+    left join mother.kittens as offspr]]></programlisting>
+
+        <para>
+            à condition que la classe <literal>Family</literal> possède le constructeur approprié.
+        </para>
+
+        <para>
+            Vous pouvez assigner des alias aux expressions sélectionnées en utilisant <literal>as</literal> :
+        </para>
+
+        <programlisting><![CDATA[select max(bodyWeight) as max, min(bodyWeight) as min, count(*) as n
+from Cat cat]]></programlisting>
+
+        <para>
+            C'est surtout utile lorsque c'est utilisé avec
+            <literal>select new map</literal> :
+        </para>
+
+        <programlisting><![CDATA[select new map( max(bodyWeight) as max, min(bodyWeight) as min, count(*) as n )
+from Cat cat]]></programlisting>
+
+        <para>
+            Cette requête retourne une <literal>Map</literal> à partir des alias vers les valeurs sélectionnées.
+        </para>
+
+    </sect1>
+
+    <sect1 id="queryhql-aggregation">
+        <title>Fonctions d'aggrégation</title>
+
+        <para>
+            Les requêtes HQL peuvent aussi retourner le résultat de fonctions d'aggrégation
+            sur les propriétés :
+        </para>
+
+        <programlisting><![CDATA[select avg(cat.weight), sum(cat.weight), max(cat.weight), count(cat)
+from Cat cat]]></programlisting>
+
+<!-- NO LONGER SUPPORTED
+        <para>
+            Collections may also appear inside aggregate functions in the <literal>select</literal>
+            clause.
+        </para>
+
+        <programlisting><![CDATA[select cat, count( elements(cat.kittens) )
+from Cat cat group by cat]]></programlisting>
+-->
+
+        <para>
+            Les fonctions supportées sont
+        </para>
+
+        <itemizedlist spacing="compact">
+            <listitem>
+                <para>
+                    <literal>avg(...), sum(...), min(...), max(...)</literal>
+                </para>
+            </listitem>
+            <listitem>
+                <para>
+                    <literal>count(*)</literal>
+                </para>
+            </listitem>
+            <listitem>
+                <para>
+                    <literal>count(...), count(distinct ...), count(all...)</literal>
+                </para>
+            </listitem>
+        </itemizedlist>
+
+        <para>
+            Vous pouvez utiliser des opérateurs arithmétiques, la concaténation, et des fonctions SQL reconnues dans la clause select :
+        </para>
+
+        <programlisting><![CDATA[select cat.weight + sum(kitten.weight)
+from Cat cat
+    join cat.kittens kitten
+group by cat.id, cat.weight]]></programlisting>
+
+        <programlisting><![CDATA[select firstName||' '||initial||' '||upper(lastName) from Person]]></programlisting>
+
+        <para>
+            Les mots clé <literal>distinct</literal> et <literal>all</literal> peuvent être utilisés et ont
+        la même signification qu'en SQL.
+        </para>
+
+        <programlisting><![CDATA[select distinct cat.name from Cat cat
+
+select count(distinct cat.name), count(cat) from Cat cat]]></programlisting>
+
+    </sect1>
+
+    <sect1 id="queryhql-polymorphism">
+        <title>Requêtes polymorphiques</title>
+
+        <para>
+            Une requête comme:
+        </para>
+
+        <programlisting><![CDATA[from Cat as cat]]></programlisting>
+
+        <para>
+            retourne non seuleument les instances de <literal>Cat</literal>, mais aussi celles des
+            sous classes comme <literal>DomesticCat</literal>. Les requêtes Hibernate peuvent nommer n'importe
+            quelle classe ou interface Java dans la clause <literal>from</literal>. La requête retournera les
+            instances de toutes les classes persistantes qui étendent cette classe ou implémente cette interface.
+        La requête suivante retournera tous les objets persistants :
+        </para>
+
+        <programlisting><![CDATA[from java.lang.Object o]]></programlisting>
+
+        <para>
+            L'interface <literal>Named</literal> peut être implémentée par plusieurs classes persistantes :
+        </para>
+
+        <programlisting><![CDATA[from Named n, Named m where n.name = m.name]]></programlisting>
+
+        <para>
+            Notez que ces deux dernières requêtes nécessitent plus d'un <literal>SELECT</literal> SQL.
+            Ce qui signifie que la clause <literal>order by</literal> ne trie pas correctement la totalité
+            des résultats (cela signifie aussi que vous ne pouvez exécuter ces requêtes en appelant
+        <literal>Query.scroll()</literal>).
+        </para>
+
+    </sect1>
+
+    <sect1 id="queryhql-where">
+        <title>La clause where</title>
+
+        <para>
+            La clause <literal>where</literal> vous permet de réduire la liste des instances retournées. 
+            Si aucun alias n'existe, vous pouvez vous référer aux propriétés par leur nom :
+        </para>
+
+        <programlisting><![CDATA[from Cat where name='Fritz']]></programlisting>
+
+        <para>
+            S'il y a un alias, utilisez un nom de propriété qualifié :
+        </para>
+
+        <programlisting><![CDATA[from Cat as cat where cat.name='Fritz']]></programlisting>
+
+        <para>
+            retourne les instances de <literal>Cat</literal> dont name est égale à 'Fritz'.
+        </para>
+
+        <programlisting><![CDATA[select foo
+from Foo foo, Bar bar
+where foo.startDate = bar.date]]></programlisting>
+
+        <para>
+            retournera les instances de <literal>Foo</literal> pour lesquelles
+            il existe une instance de <literal>bar</literal> avec la
+            propriété <literal>date</literal> est égale à la
+            propriété <literal>startDate</literal> de <literal>Foo</literal>.
+            Les expressions utilisant la navigation rendent la clause <literal>where</literal>
+        extrêmement puissante. Soit :
+        </para>
+
+        <programlisting><![CDATA[from Cat cat where cat.mate.name is not null]]></programlisting>
+
+        <para>
+            Cette requête se traduit en SQL par une jointure interne à une table.
+        Si vous souhaitez écrire quelque chose comme :
+        </para>
+
+        <programlisting><![CDATA[from Foo foo
+where foo.bar.baz.customer.address.city is not null]]></programlisting>
+
+        <para>
+            vous finiriez avec une requête qui nécessiterait quatre jointures en SQL.
+        </para>
+
+        <para>
+            L'opérateur <literal>=</literal> peut être utilisé pour comparer aussi bien des propriétés que des instances :
+        </para>
+
+        <programlisting><![CDATA[from Cat cat, Cat rival where cat.mate = rival.mate]]></programlisting>
+
+        <programlisting><![CDATA[select cat, mate
+from Cat cat, Cat mate
+where cat.mate = mate]]></programlisting>
+
+        <para>
+            La propriété spéciale (en minuscule) <literal>id</literal> peut être utilisée
+            pour faire référence à l'identifiant d'un objet (vous pouvez aussi utiliser
+        le nom de cette propriété).
+        </para>
+
+        <programlisting><![CDATA[from Cat as cat where cat.id = 123
+
+from Cat as cat where cat.mate.id = 69]]></programlisting>
+
+        <para>
+            La seconde requête est particulièrement efficace. Aucune jointure n'est nécessaire !
+        </para>
+
+        <para>
+            Les propriétés d'un identifiant composé peuvent aussi être utilisées. Supposez que
+            <literal>Person</literal> ait un identifiant composé de <literal>country</literal> et
+            <literal>medicareNumber</literal>.
+        </para>
+
+        <programlisting><![CDATA[from bank.Person person
+where person.id.country = 'AU'
+    and person.id.medicareNumber = 123456]]></programlisting>
+
+        <programlisting><![CDATA[from bank.Account account
+where account.owner.id.country = 'AU'
+    and account.owner.id.medicareNumber = 123456]]></programlisting>
+
+        <para>
+            Une fois de plus, la seconde requête ne nécessite pas de jointure.
+        </para>
+
+        <para>
+            De même, la propriété spéciale <literal>class</literal> interroge la valeur discriminante
+            d'une instance dans le cas d'une persistance polymorphique. Le nom d'une classe Java incorporée
+        dans la clause where sera traduite par sa valeur discriminante.
+        </para>
+
+        <programlisting><![CDATA[from Cat cat where cat.class = DomesticCat]]></programlisting>
+
+        <para>
+            Vous pouvez aussi spécifier les propriétés des composants ou types utilisateurs composés
+            (components, composite user types etc). N'essayez jamais d'utiliser un expression de navigation
+            qui se terminerait par une propriété de type composant (qui est différent d'une propriété d'un
+            composant). Par exemple, si <literal>store.owner</literal> est une entité avec un composant
+        <literal>address</literal>
+        </para>
+
+        <programlisting><![CDATA[store.owner.address.city    // okay
+store.owner.address         // error!]]></programlisting>
+
+        <para>
+            Un type "any" possède les propriétés spéciales <literal>id</literal> et <literal>class</literal>,
+            qui nous permettent d'exprimer une jointure de la manière suivante (où <literal>AuditLog.item</literal>
+            est une propriété mappée avec <literal>&lt;any&gt;</literal>).
+        </para>
+
+        <programlisting><![CDATA[from AuditLog log, Payment payment
+where log.item.class = 'Payment' and log.item.id = payment.id]]></programlisting>
+
+        <para>
+            Dans la requête précédente, notez que <literal>log.item.class</literal> et <literal>payment.class</literal>
+            feraient référence à des valeurs de colonnes de la base de données complètement différentes.
+        </para>
+
+    </sect1>
+
+    <sect1 id="queryhql-expressions">
+        <title>Expressions</title>
+
+        <para>
+            Les expressions permises dans la clause <literal>where</literal> incluent
+        la plupart des choses que vous pouvez utiliser en SQL :
+        </para>
+
+        <itemizedlist spacing="compact">
+            <listitem>
+                <para>
+                    opérateurs mathématiques <literal>+, -, *, /</literal>
+                </para>
+            </listitem>
+            <listitem>
+                <para>
+                    opérateur de comparaison binaire <literal>=, &gt;=, &lt;=, &lt;&gt;, !=, like</literal>
+                </para>
+            </listitem>
+            <listitem>
+                <para>
+                    opérateurs logiques <literal>and, or, not</literal>
+                </para>
+            </listitem>
+            <listitem>
+                <para>
+                    Parenthèses <literal>( )</literal>, indiquant un regroupement
+                </para>
+            </listitem>
+            <listitem>
+                <para>
+                    <literal>in</literal>,
+                    <literal>not in</literal>,
+                    <literal>between</literal>,
+                    <literal>is null</literal>,
+                    <literal>is not null</literal>,
+                    <literal>is empty</literal>,
+                    <literal>is not empty</literal>,
+                    <literal>member of</literal> and
+                    <literal>not member of</literal>
+                </para>
+            </listitem>
+            <listitem>
+                <para>
+                    "Simple" case, <literal>case ... when ... then ... else ... end</literal>, and
+                    "searched" case, <literal>case when ... then ... else ... end</literal>
+                </para>
+            </listitem>
+            <listitem>
+                <para>
+                    concatenation de chaîne de caractères <literal>...||...</literal> ou <literal>concat(...,...)</literal>
+                </para>
+            </listitem>
+            <listitem>
+                <para>
+                    <literal>current_date()</literal>, <literal>current_time()</literal>,
+                    <literal>current_timestamp()</literal>
+                </para>
+            </listitem>
+            <listitem>
+                <para>
+                    <literal>second(...)</literal>, <literal>minute(...)</literal>,
+                    <literal>hour(...)</literal>, <literal>day(...)</literal>,
+                    <literal>month(...)</literal>, <literal>year(...)</literal>,
+                </para>
+            </listitem>
+            <listitem>
+                <para>
+                    N'importe quel fonction ou opérateur défini par EJB-QL 3.0 : <literal>substring(), trim(),
+                    lower(), upper(), length(), locate(), abs(), sqrt(), bit_length(), mod()</literal>
+                </para>
+            </listitem>
+            <listitem>
+                <para>
+                    <literal>coalesce()</literal> et <literal>nullif()</literal>
+                </para>
+            </listitem>
+            <listitem>
+                <para>
+                    <literal>str()</literal> pour convertir des valeurs numériques ou temporelles vers une chaîne de caractères lisible
+                </para>
+            </listitem>
+            <listitem>
+                <para>
+                    <literal>cast(... as ...)</literal>, où le second argument est le nom d'un type Hibernate, et <literal>extract(... from ...)</literal> si le
+                    <literal>cast()</literal> ANSI et <literal>extract()</literal> sont supportés par la base de données sous-jacente
+                </para>
+            </listitem>
+            <listitem>
+                <para>
+                    La fonction HQL <literal>index()</literal>, qui s'applique aux alias d'une collection indexée jointe
+                </para>
+            </listitem>
+            <listitem>
+                <para>
+                    Les fonctions HQL qui s'appliquent expressions représentant des collections : <literal>size(),
+                    minelement(), maxelement(), minindex(), maxindex()</literal>, ainsi que les fonctions spéciales <literal>elements()</literal> 
+                    et <literal>indices</literal> qui peuvent être quantifiées en utilisant <literal>some, all, exists, any, in</literal>.
+                </para>
+            </listitem>
+            <listitem>
+                <para>
+                    N'importe quelle fonction scalaire supportée par la base de données comme
+                    <literal>sign()</literal>,
+                    <literal>trunc()</literal>, <literal>rtrim()</literal>, <literal>sin()</literal>
+                </para>
+            </listitem>
+            <listitem>
+                <para>
+                    Les paramètres positionnels de JDBC
+                    <literal>?</literal>
+                </para>
+            </listitem>
+            <listitem>
+                <para>
+                    paramètres nommés <literal>:name</literal>, <literal>:start_date</literal>, <literal>:x1</literal>
+                </para>
+            </listitem>
+            <listitem>
+                <para>
+                    littéral SQL <literal>'foo'</literal>, <literal>69</literal>, <literal>'1970-01-01 10:00:01.0'</literal>
+                </para>
+            </listitem>
+            <listitem>
+                <para>
+                    Constantes Java <literal>public static final</literal> <literal>eg.Color.TABBY</literal>
+                </para>
+            </listitem>
+        </itemizedlist>
+
+        <para>
+            <literal>in</literal> et <literal>between</literal> peuvent être utilisés comme suit :
+        </para>
+
+        <programlisting><![CDATA[from DomesticCat cat where cat.name between 'A' and 'B']]></programlisting>
+
+        <programlisting><![CDATA[from DomesticCat cat where cat.name in ( 'Foo', 'Bar', 'Baz' )]]></programlisting>
+
+        <para>
+            et la forme négative peut être écrite
+        </para>
+
+        <programlisting><![CDATA[from DomesticCat cat where cat.name not between 'A' and 'B']]></programlisting>
+
+        <programlisting><![CDATA[from DomesticCat cat where cat.name not in ( 'Foo', 'Bar', 'Baz' )]]></programlisting>
+
+        <para>
+            De même, <literal>is null</literal> et <literal>is not null</literal> peuvent être utilisés pour tester
+        les valeurs nulle.
+        </para>
+
+        <para>
+            Les booléens peuvent être facilement utilisés en déclarant les substitutions de requêtes dans la
+        configuration Hibernate :
+        </para>
+
+        <programlisting><![CDATA[<property name="hibernate.query.substitutions">true 1, false 0</property>]]></programlisting>
+
+        <para>
+            Ce qui remplacera les mots clés <literal>true</literal> et <literal>false</literal> par
+            <literal>1</literal> et <literal>0</literal> dans la traduction SQL du HQL suivant :
+        </para>
+
+        <programlisting><![CDATA[from Cat cat where cat.alive = true]]></programlisting>
+
+        <para>
+            Vous pouvez tester la taille d'une collection par la propriété spéciale <literal>size</literal>, ou
+            la fonction spéciale <literal>size()</literal>.
+        </para>
+
+        <programlisting><![CDATA[from Cat cat where cat.kittens.size > 0]]></programlisting>
+
+        <programlisting><![CDATA[from Cat cat where size(cat.kittens) > 0]]></programlisting>
+
+        <para>
+            Pour les collections indexées, vous pouvez faire référence aux indices minimum et maximum en
+            utilisant les fonctions <literal>minindex</literal> and <literal>maxindex</literal>. De manière similaire,
+            vous pouvez faire référence aux éléments minimum et maximum d'une collection de type basiques
+        en utilisant les fonctions <literal>minelement</literal> et <literal>maxelement</literal>.
+        </para>
+
+        <programlisting><![CDATA[from Calendar cal where maxelement(cal.holidays) > current date]]></programlisting>
+
+        <programlisting><![CDATA[from Order order where maxindex(order.items) > 100]]></programlisting>
+
+        <programlisting><![CDATA[from Order order where minelement(order.items) > 10000]]></programlisting>
+
+        <para>
+            Les fonctions SQL <literal>any, some, all, exists, in</literal> supportent que leur soient passées
+            l'élément, l'index d'une collection (fonctions <literal>elements</literal> et <literal>indices</literal>)
+        ou le résultat d'une sous requête (voir ci dessous).
+        </para>
+
+        <programlisting><![CDATA[select mother from Cat as mother, Cat as kit
+where kit in elements(foo.kittens)]]></programlisting>
+
+        <programlisting><![CDATA[select p from NameList list, Person p
+where p.name = some elements(list.names)]]></programlisting>
+
+        <programlisting><![CDATA[from Cat cat where exists elements(cat.kittens)]]></programlisting>
+
+        <programlisting><![CDATA[from Player p where 3 > all elements(p.scores)]]></programlisting>
+
+        <programlisting><![CDATA[from Show show where 'fizard' in indices(show.acts)]]></programlisting>
+
+        <para>
+            Notez que l'écriture de - <literal>size</literal>, <literal>elements</literal>,
+            <literal>indices</literal>, <literal>minindex</literal>, <literal>maxindex</literal>,
+            <literal>minelement</literal>, <literal>maxelement</literal> - peuvent seulement être utilisée dans la clause where dans Hibernate3.
+        </para>
+
+        <para>
+            Les éléments de collections indexées (arrays, lists, maps) peuvent être référencés via index
+        (dans une clause where seulement) :
+        </para>
+
+        <programlisting><![CDATA[from Order order where order.items[0].id = 1234]]></programlisting>
+
+        <programlisting><![CDATA[select person from Person person, Calendar calendar
+where calendar.holidays['national day'] = person.birthDay
+    and person.nationality.calendar = calendar]]></programlisting>
+
+        <programlisting><![CDATA[select item from Item item, Order order
+where order.items[ order.deliveredItemIndices[0] ] = item and order.id = 11]]></programlisting>
+
+        <programlisting><![CDATA[select item from Item item, Order order
+where order.items[ maxindex(order.items) ] = item and order.id = 11]]></programlisting>
+
+        <para>
+            L'expression entre <literal>[]</literal> peut même être une expression arithmétique.
+        </para>
+
+        <programlisting><![CDATA[select item from Item item, Order order
+where order.items[ size(order.items) - 1 ] = item]]></programlisting>
+
+        <para>
+            HQL propose aussi une fonction <literal>index()</literal> interne, pour les éléments
+        d'une association one-to-many ou d'une collections de valeurs.
+        </para>
+
+        <programlisting><![CDATA[select item, index(item) from Order order
+    join order.items item
+where index(item) < 5]]></programlisting>
+
+        <para>
+            Les fonctions SQL scalaires supportées par la base de données utilisée peuvent être utilisées
+        </para>
+
+        <programlisting><![CDATA[from DomesticCat cat where upper(cat.name) like 'FRI%']]></programlisting>
+
+        <para>
+            Si vous n'êtes pas encore convaincu par tout cela, imaginez la taille et l'illisibilité qui caractériseraient
+        la transformation SQL de la requête HQL suivante :
+        </para>
+
+        <programlisting><![CDATA[select cust
+from Product prod,
+    Store store
+    inner join store.customers cust
+where prod.name = 'widget'
+    and store.location.name in ( 'Melbourne', 'Sydney' )
+    and prod = all elements(cust.currentOrder.lineItems)]]></programlisting>
+
+        <para>
+            <emphasis>Un indice :</emphasis> cela donnerait quelque chose comme
+        </para>
+
+        <programlisting><![CDATA[SELECT cust.name, cust.address, cust.phone, cust.id, cust.current_order
+FROM customers cust,
+    stores store,
+    locations loc,
+    store_customers sc,
+    product prod
+WHERE prod.name = 'widget'
+    AND store.loc_id = loc.id
+    AND loc.name IN ( 'Melbourne', 'Sydney' )
+    AND sc.store_id = store.id
+    AND sc.cust_id = cust.id
+    AND prod.id = ALL(
+        SELECT item.prod_id
+        FROM line_items item, orders o
+        WHERE item.order_id = o.id
+            AND cust.current_order = o.id
+    )]]></programlisting>
+
+    </sect1>
+
+    <sect1 id="queryhql-ordering">
+        <title>La clause order by</title>
+
+        <para>
+            La liste retounée par la requête peut être triée par n'importe quelle propriété de la classe ou
+        du composant retourné :
+        </para>
+
+        <programlisting><![CDATA[from DomesticCat cat
+order by cat.name asc, cat.weight desc, cat.birthdate]]></programlisting>
+
+        <para>
+            Le mot optionnel <literal>asc</literal> ou <literal>desc</literal> indique respectivement si le tri
+        doit être croissant ou décroissant.
+        </para>
+    </sect1>
+
+    <sect1 id="queryhql-grouping">
+        <title>La clause group by</title>
+
+        <para>
+            Si la requête retourne des valeurs aggrégées, celles ci peuvent être groupées par propriété ou composant :
+        </para>
+
+        <programlisting><![CDATA[select cat.color, sum(cat.weight), count(cat)
+from Cat cat
+group by cat.color]]></programlisting>
+
+        <programlisting><![CDATA[select foo.id, avg(name), max(name)
+from Foo foo join foo.names name
+group by foo.id]]></programlisting>
+
+        <para>
+            Une clause <literal>having</literal> est aussi permise.
+        </para>
+
+        <programlisting><![CDATA[select cat.color, sum(cat.weight), count(cat)
+from Cat cat
+group by cat.color
+having cat.color in (eg.Color.TABBY, eg.Color.BLACK)]]></programlisting>
+
+        <para>
+            Les fonctions SQL et les fonctions d'aggrégations sont permises dans les clauses <literal>having</literal>
+            et <literal>order by</literal>, si elles sont supportées par la base de données (ce que ne fait pas MySQL par exemple).
+        </para>
+
+        <programlisting><![CDATA[select cat
+from Cat cat
+    join cat.kittens kitten
+group by cat
+having avg(kitten.weight) > 100
+order by count(kitten) asc, sum(kitten.weight) desc]]></programlisting>
+
+        <para>
+            Notez que ni la clause <literal>group by</literal> ni la clause
+            <literal>order by</literal> ne peuvent contenir d'expressions arithmétiques.
+        </para>
+
+    </sect1>
+
+    <sect1 id="queryhql-subqueries" revision="2">
+        <title>Sous-requêtes</title>
+
+        <para>
+            Pour les bases de données le supportant, Hibernate supporte les sous requêtes dans les requêtes.
+            Une sous requête doit être entre parenthèses (souvent pour un appel à une fonction d'agrégation SQL)
+            Même les sous requêtes corrélées (celles qui font référence à un alias de la requête principale) sont
+        supportées.
+        </para>
+
+        <programlisting><![CDATA[from Cat as fatcat
+where fatcat.weight > (
+    select avg(cat.weight) from DomesticCat cat
+)]]></programlisting>
+
+        <programlisting><![CDATA[from DomesticCat as cat
+where cat.name = some (
+    select name.nickName from Name as name
+)]]></programlisting>
+
+        <programlisting><![CDATA[from Cat as cat
+where not exists (
+    from Cat as mate where mate.mate = cat
+)]]></programlisting>
+
+        <programlisting><![CDATA[from DomesticCat as cat
+where cat.name not in (
+    select name.nickName from Name as name
+)]]></programlisting>
+
+        <programlisting><![CDATA[select cat.id, (select max(kit.weight) from cat.kitten kit)
+from Cat as cat]]></programlisting>
+
+        <para>
+            Notez que les sous-requêtes HQL peuvent arriver seulememnt dans les clauses select ou where.
+        </para>
+
+        <para>
+            Pour des sous-requêtes avec plus d'une expression dans le select, vous pouvez utiliser un constructeur de tuples :
+        </para>
+
+        <programlisting><![CDATA[from Cat as cat
+where not ( cat.name, cat.color ) in (
+    select cat.name, cat.color from DomesticCat cat
+)]]></programlisting>
+
+        <para>
+            Notez que sur certaines bases de données (mais par Oracle ou HSQL), vous pouvez utiliser des constructeurs de tuples 
+            dans d'autres contextes, par exemple lors du requêtage de composants ou de types utilisateur composites :
+        </para>
+
+        <programlisting><![CDATA[from Person where name = ('Gavin', 'A', 'King')]]></programlisting>
+
+        <para>
+            Ce qui est équivalent à la forme plus verbeuse suivante :
+        </para>
+
+        <programlisting><![CDATA[from Person where name.first = 'Gavin' and name.initial = 'A' and name.last = 'King')]]></programlisting>
+
+        <para>
+            Il y a deux bonnes raisons que vous ne puissiez ne pas vouloir faire cette sorte de choses : d'abord, ce n'est
+            pas complètement portable entre les plateformes de base de données ; deuxièmement, la requête est maintenant
+            dépendante de l'ordre des propriétés dans le document de mapping.
+        </para>
+
+    </sect1>
+
+    <sect1 id="queryhql-examples">
+        <title>Exemples HQL</title>
+
+        <para>
+            Les requêtes Hibernate peuvent être relativement puissantes et complexes. En fait, la puissance
+            du langage de requêtage est l'un des avantages principaux d'Hibernate. Voici quelques exemples
+            très similaires aux requêtes que nous avons utilisées lors d'un récent projet. Notez que la plupart
+        des requêtes que vous écrirez seront plus simples que les exemples suivantes !
+        </para>
+
+        <para>
+            La requête suivante retourne l'id de commande (order), le nombre d'articles (items) et la valeur
+            totale de la commande (order) pour toutes les commandes non payées d'un client (customer) particulier
+            pour un total minimum donné, le tout trié par la valeur totale. La requête SQL générée sur les tables
+            <literal>ORDER</literal>, <literal>ORDER_LINE</literal>, <literal>PRODUCT</literal>,
+            <literal>CATALOG</literal> et <literal>PRICE</literal> est composée de quatre jointures interne ainsi que
+        d'une sous-requête (non corrélée).
+        </para>
+
+        <programlisting><![CDATA[select order.id, sum(price.amount), count(item)
+from Order as order
+    join order.lineItems as item
+    join item.product as product,
+    Catalog as catalog
+    join catalog.prices as price
+where order.paid = false
+    and order.customer = :customer
+    and price.product = product
+    and catalog.effectiveDate < sysdate
+    and catalog.effectiveDate >= all (
+        select cat.effectiveDate
+        from Catalog as cat
+        where cat.effectiveDate < sysdate
+    )
+group by order
+having sum(price.amount) > :minAmount
+order by sum(price.amount) desc]]></programlisting>
+
+        <para>
+            Quel monstre !
+            En principe, nous ne sommes pas très fan des sous-requêtes, la requête ressemblait donc plutôt
+        à cela :
+        </para>
+
+        <programlisting><![CDATA[select order.id, sum(price.amount), count(item)
+from Order as order
+    join order.lineItems as item
+    join item.product as product,
+    Catalog as catalog
+    join catalog.prices as price
+where order.paid = false
+    and order.customer = :customer
+    and price.product = product
+    and catalog = :currentCatalog
+group by order
+having sum(price.amount) > :minAmount
+order by sum(price.amount) desc]]></programlisting>
+
+        <para>
+            La requête suivante compte le nombre de paiements (payments) pour chaque status, en excluant
+            les paiements dans le status <literal>AWAITING_APPROVAL</literal> où le changement de status
+            le plus récent à été fait par l'utilisateur courant. En SQL, cette requête effectue deux
+            jointures internes et des sous requêtes corrélées sur les tables <literal>PAYMENT</literal>,
+        <literal>PAYMENT_STATUS</literal> et <literal>PAYMENT_STATUS_CHANGE</literal>.
+        </para>
+
+        <programlisting><![CDATA[select count(payment), status.name
+from Payment as payment
+    join payment.currentStatus as status
+    join payment.statusChanges as statusChange
+where payment.status.name <> PaymentStatus.AWAITING_APPROVAL
+    or (
+        statusChange.timeStamp = (
+            select max(change.timeStamp)
+            from PaymentStatusChange change
+            where change.payment = payment
+        )
+        and statusChange.user <> :currentUser
+    )
+group by status.name, status.sortOrder
+order by status.sortOrder]]></programlisting>
+
+        <para>
+            Si nous avions mappé la collection <literal>statusChanges</literal> comme une liste, au lieu d'un ensemble,
+            la requête aurait été plus facile à écrire.
+        </para>
+
+        <programlisting><![CDATA[select count(payment), status.name
+from Payment as payment
+    join payment.currentStatus as status
+where payment.status.name <> PaymentStatus.AWAITING_APPROVAL
+    or payment.statusChanges[ maxIndex(payment.statusChanges) ].user <> :currentUser
+group by status.name, status.sortOrder
+order by status.sortOrder]]></programlisting>
+
+        <para>
+            La requête qui suit utilise la fonction de MS SQL <literal>isNull()</literal> pour retourner
+            tous les comptes (accounts) et paiements (payments) impayés pour l'organisation à laquelle
+            l'uilisateur (user) courant appartient. Elle est traduite en SQL par trois jointures internes,
+            une jointure externe ainsi qu'une sous requête sur les tables <literal>ACCOUNT</literal>, <literal>PAYMENT</literal>,
+            <literal>PAYMENT_STATUS</literal>, <literal>ACCOUNT_TYPE</literal>, <literal>ORGANIZATION</literal> et
+            <literal>ORG_USER</literal>.
+        </para>
+
+        <programlisting><![CDATA[select account, payment
+from Account as account
+    left outer join account.payments as payment
+where :currentUser in elements(account.holder.users)
+    and PaymentStatus.UNPAID = isNull(payment.currentStatus.name, PaymentStatus.UNPAID)
+order by account.type.sortOrder, account.accountNumber, payment.dueDate]]></programlisting>
+
+        <para>
+            Pour d'autres base de données, nous aurions dû faire sans la sous-requête (corrélée).
+        </para>
+
+        <programlisting><![CDATA[select account, payment
+from Account as account
+    join account.holder.users as user
+    left outer join account.payments as payment
+where :currentUser = user
+    and PaymentStatus.UNPAID = isNull(payment.currentStatus.name, PaymentStatus.UNPAID)
+order by account.type.sortOrder, account.accountNumber, payment.dueDate]]></programlisting>
+
+   </sect1>
+
+    <sect1 id="queryhql-bulk" revision="2">
+        <title>Mise à jour et suppression</title>
+
+        <para>
+            HQL supporte maintenant les expressions <literal>update</literal>, <literal>delete</literal> et
+            <literal>insert ... select ...</literal>.
+            Voir <xref linkend="batch-direct"/> pour les détails.
+        </para>
+    </sect1>
+
+    <sect1 id="queryhql-tipstricks">
+        <title>Trucs &amp; Astuces</title>
+
+        <para>
+            Vous pouvez compter le nombre de résultats d'une requête sans les retourner :
+        </para>
+
+        <programlisting><![CDATA[( (Integer) session.createQuery("select count(*) from ....").iterate().next() ).intValue()]]></programlisting>
+
+        <para>
+            Pour trier les résultats par la taille d'une collection, utilisez la requête suivante :
+        </para>
+
+        <programlisting><![CDATA[select usr.id, usr.name
+from User as usr
+    left join usr.messages as msg
+group by usr.id, usr.name
+order by count(msg)]]></programlisting>
+
+        <para>
+            Si votre base de données supporte les sous-requêtes, vous pouvez placer des
+        conditions sur la taille de la sélection dans la clause where de votre requête:
+        </para>
+
+        <programlisting><![CDATA[from User usr where size(usr.messages) >= 1]]></programlisting>
+
+        <para>
+            Si votre base de données ne supporte pas les sous-requêtes, utilisez la requête suivante :
+        </para>
+
+        <programlisting><![CDATA[select usr.id, usr.name
+from User usr.name
+    join usr.messages msg
+group by usr.id, usr.name
+having count(msg) >= 1]]></programlisting>
+
+        <para>
+            Cette solution ne peut pas retourner un <literal>User</literal> avec zéro message
+            à cause de la jointure interne, la forme suivante peut donc être utile :
+        </para>
+
+        <programlisting><![CDATA[select usr.id, usr.name
+from User as usr
+    left join usr.messages as msg
+group by usr.id, usr.name
+having count(msg) = 0]]></programlisting>
+
+        <para>
+            Les propriétés d'un JavaBean peuvent être injectées dans les paramètres nommés d'un requête :
+        </para>
+
+        <programlisting><![CDATA[Query q = s.createQuery("from foo Foo as foo where foo.name=:name and foo.size=:size");
+q.setProperties(fooBean); // fooBean has getName() and getSize()
+List foos = q.list();]]></programlisting>
+
+        <para>
+            Les collections sont paginables via l'utilisation de l'interface <literal>Query</literal> avec un filtre :
+        </para>
+
+        <programlisting><![CDATA[Query q = s.createFilter( collection, "" ); // the trivial filter
+q.setMaxResults(PAGE_SIZE);
+q.setFirstResult(PAGE_SIZE * pageNumber);
+List page = q.list();]]></programlisting>
+
+        <para>
+            Les éléments d'une collection peuvent être triés ou groupés en utilisant un filtre de requête :
+        </para>
+
+        <programlisting><![CDATA[Collection orderedCollection = s.filter( collection, "order by this.amount" );
+Collection counts = s.filter( collection, "select this.type, count(this) group by this.type" );]]></programlisting>
+
+        <para>
+            Vous pouvez récupérer la taille d'une collection sans l'initialiser :
+        </para>
+
+        <programlisting><![CDATA[( (Integer) session.createQuery("select count(*) from ....").iterate().next() ).intValue();]]></programlisting>
+
+    </sect1>
+
+</chapter>

Copied: core/trunk/documentation/manual/fr-FR/src/main/docbook/content/query_sql.xml (from rev 14070, core/trunk/documentation/manual/fr-FR/src/main/docbook/modules/query_sql.xml)
===================================================================
--- core/trunk/documentation/manual/fr-FR/src/main/docbook/content/query_sql.xml	                        (rev 0)
+++ core/trunk/documentation/manual/fr-FR/src/main/docbook/content/query_sql.xml	2007-10-09 18:28:36 UTC (rev 14074)
@@ -0,0 +1,606 @@
+<?xml version="1.0" encoding="ISO-8859-1"?>
+<chapter id="querysql" revision="2">
+    <title>SQL natif</title>
+
+    <para>
+        Vous pouvez aussi écrire vos requêtes dans le dialecte SQL natif de votre base de données.
+        Ceci est utile si vous souhaitez utiliser les fonctionnalités spécifiques de votre base de
+        données comme le mot clé <literal>CONNECT</literal> d'Oracle. Cette fonctionnalité offre par ailleurs un moyen
+        de migration plus propre et doux d'une application basée sur SQL/JDBC vers
+        une application Hibernate.
+    </para>
+
+  <para>Hibernate3 vous permet de spécifier du SQL écrit à la main (incluant les procédures stockées) 
+  pour toutes les opérations de création, mise à jour, suppression et chargement.</para>
+
+  <sect1 id="querysql-creating" revision="3">
+    <title>Utiliser une <literal>SQLQuery</literal></title>
+
+    <para>L'exécution des requêtes en SQL natif est contrôlée par l'interface <literal>SQLQuery</literal>,
+        laquelle est obtenue en appelant <literal>Session.createSQLQuery()</literal>.
+        Dans des cas extrêmement simples, nous pouvons utiliser la forme suivante :
+    </para>
+
+    <programlisting>List cats = sess.createSQLQuery("select * from cats")
+    .addEntity(Cat.class)
+    .list();</programlisting>
+
+    <para>Cette requête a spécifié :</para>
+
+    <itemizedlist>
+      <listitem>
+        <para>la requête SQL</para>
+      </listitem>
+
+      <listitem>
+        <para>l'entité retournée par la requête</para>
+      </listitem>
+    </itemizedlist>
+
+    <para>
+        Ici, les noms de colonne des résultats sont supposés être les mêmes que les noms de colonne spécifiés dans le
+        document de mapping. Cela peut être problématique pour des requêtes SQL qui joignent de multiple tables, puisque
+        les mêmes noms de colonne peuvent apparaître dans plus d'une table. La forme suivante n'est pas vulnérable à la
+        duplication des noms de colonne :
+    </para>
+
+    <programlisting>List cats = sess.createSQLQuery("select {cat.*} from cats cat")
+    .addEntity("cat", Cat.class)
+    .list();</programlisting>
+
+    <para>Cette requête a spécifié :</para>
+
+    <itemizedlist>
+      <listitem>
+        <para>la requête SQL, avec un paramètre fictif pour Hibernate pour injecter les alias de colonne</para>
+      </listitem>
+
+      <listitem>
+        <para>l'entité retournée par la requête, et son alias de table SQL</para>
+      </listitem>
+    </itemizedlist>
+
+    <para>
+        La méthode <literal>addEntity()</literal> associe l'alias de la table SQL
+        avec la classe de l'entité retournée, et détermine la forme de l'ensemble des résultats de la requête.
+    </para>
+
+    <para>
+        La méthode <literal>addJoin()</literal> peut être utilisée pour charger des associations vers d'autres
+        entités et collections.
+    </para>
+
+    <programlisting>List cats = sess.createSQLQuery(
+        "select {cat.*}, {kitten.*} from cats cat, cats kitten where kitten.mother = cat.id"
+    )
+    .addEntity("cat", Cat.class)
+    .addJoin("kitten", "cat.kittens")
+    .list();</programlisting>
+
+    <para>
+        Une requête SQL native pourrait retourner une simple valeur scalaire ou une combinaison de scalaires et d'entités.
+    </para>
+
+    <programlisting>Double max = (Double) sess.createSQLQuery("select max(cat.weight) as maxWeight from cats cat")
+        .addScalar("maxWeight", Hibernate.DOUBLE);
+        .uniqueResult();</programlisting>
+
+    <para>Vous pouvez alternativement décrire les informations de mapping des résultats dans vos fichiers hbm 
+    et les utiliser pour vos requêtes.</para>
+
+    <programlisting>List cats = sess.createSQLQuery(
+        "select {cat.*}, {kitten.*} from cats cat, cats kitten where kitten.mother = cat.id"
+    )
+    .setResultSetMapping("catAndKitten")
+    .list();</programlisting>
+  </sect1>
+
+  <sect1 id="querysql-aliasreferences">
+      <title>Alias et références de propriété</title>
+
+    <para>
+        La notation <literal>{cat.*}</literal> utilisée au-dessus est un raccourci pour "toutes les propriétés".
+        Alternativement, vous pouvez lister explicitement les colonnes, mais même ce cas que nous laissons à Hibernate
+        injecte des alias de colonne SQL pour chaque propriété. Le remplaçant pour un alias de colonne 
+        est juste le nom de la propriété qualifié par l'alias de la table.
+        Dans l'exemple suivant, nous récupérons des <literal>Cat</literal>s à partir d'une table différente
+        (<literal>cat_log</literal>) de celle déclarée dans les méta-données de mapping.
+        Notez que nous pouvons même utiliser les alias de propriété dans la clause "where" si nous le souhaitons.
+    </para>
+
+    <para>
+        La syntaxe <literal>{}</literal> <emphasis>n'est pas</emphasis> requise pour le requêtes nommées. Voir
+        <xref linkend="querysql-namedqueries" />.
+    </para>
+
+    <programlisting>String sql = "select cat.originalId as {cat.id}, " +
+    "cat.mateid as {cat.mate}, cat.sex as {cat.sex}, " +
+    "cat.weight*10 as {cat.weight}, cat.name as {cat.name} " +
+    "from cat_log cat where {cat.mate} = :catId"
+
+List loggedCats = sess.createSQLQuery(sql)
+    .addEntity("cat", Cat.class)
+    .setLong("catId", catId)
+    .list();</programlisting>
+
+    <para>
+        <emphasis>À noter :</emphasis> si vous listez chaque propriété explicitement, vous devez inclure 
+        toutes les propriétés de la classe <emphasis>et ses sous-classes</emphasis> !
+    </para>
+
+    <para>
+        La table suivante montre les différentes possibilités d'utilisation de l'injection d'alias. À noter : les noms
+        des alias dans le résultat sont des exemples, chaque alias aura un nom unique et probablement différent lors de l'utilisation.
+    </para>
+
+    <table frame="topbot" id="aliasinjection-summary">
+      <title>Noms d'injection d'alias</title>
+
+      <tgroup cols="4">
+        <colspec colwidth="1*" />
+
+        <colspec colwidth="1*" />
+
+        <colspec colwidth="2.5*" />
+
+        <thead>
+          <row>
+            <entry>Description</entry>
+
+            <entry>Syntaxe</entry>
+
+            <entry>Exemple</entry>
+          </row>
+        </thead>
+
+        <tbody>
+          <row>
+            <entry>Une simple propriété</entry>
+
+            <entry><literal>{[aliasname].[propertyname]}</literal></entry>
+
+            <entry><literal>A_NAME as {item.name}</literal></entry>
+          </row>
+
+          <row>
+            <entry>Une propriété composée</entry>
+
+            <entry><literal>{[aliasname].[componentname].[propertyname]}</literal></entry>
+
+            <entry><literal>CURRENCY as {item.amount.currency}, VALUE as
+            {item.amount.value}</literal></entry>
+          </row>
+
+          <row>
+            <entry>Discriminant d'une entité</entry>
+
+            <entry><literal>{[aliasname].class}</literal></entry>
+
+            <entry><literal>DISC as {item.class}</literal></entry>
+          </row>
+
+          <row>
+            <entry>Toutes les propriétés d'une entité</entry>
+
+            <entry><literal>{[aliasname].*}</literal></entry>
+
+            <entry><literal>{item.*}</literal></entry>
+          </row>
+
+          <row>
+            <entry>Une clef de collection</entry>
+
+            <entry><literal>{[aliasname].key}</literal></entry>
+
+            <entry><literal>ORGID as {coll.key}</literal></entry>
+          </row>
+
+          <row>
+            <entry>L'identifiant d'une collection</entry>
+
+            <entry><literal>{[aliasname].id}</literal></entry>
+
+            <entry><literal>EMPID as {coll.id}</literal></entry>
+          </row>
+
+          <row>
+            <entry>L'élément d'une collection</entry>
+
+            <entry><literal>{[aliasname].element}</literal></entry>
+
+            <entry><literal>XID as {coll.element}</literal></entry>
+
+            <entry></entry>
+          </row>
+
+          <row>
+            <entry>Propriété de l'élément dans la collection</entry>
+
+            <entry><literal>{[aliasname].element.[propertyname]}</literal></entry>
+
+            <entry><literal>NAME as {coll.element.name}</literal></entry>
+          </row>
+
+          <row>
+            <entry>Toutes les propriétés de l'élément dans la collection</entry>
+
+            <entry><literal>{[aliasname].element.*}</literal></entry>
+
+            <entry><literal>{coll.element.*}</literal></entry>
+          </row>
+
+          <row>
+            <entry>Toutes les propriétés de la collection</entry>
+
+            <entry><literal>{[aliasname].*}</literal></entry>
+
+            <entry><literal>{coll.*}</literal></entry>
+          </row>
+        </tbody>
+      </tgroup>
+    </table>
+  </sect1>
+
+  <sect1 id="querysql-namedqueries" revision="3">
+    <title>Requêtes SQL nommées</title>
+
+    <para>
+        Les requêtes SQL nommées peuvent être définies dans le document de mapping
+        et appelées exactement de la même manière qu'un requête HQL nommée. Dans ce
+        cas, nous <emphasis>n'avons pas besoin</emphasis> d'appeler <literal>addEntity()</literal>.
+    </para>
+
+    <programlisting>&lt;sql-query name="persons"&gt;
+    &lt;return alias="person" class="eg.Person"/&gt;
+    SELECT person.NAME AS {person.name},
+           person.AGE AS {person.age},
+           person.SEX AS {person.sex}
+    FROM PERSON person
+    WHERE person.NAME LIKE :namePattern
+&lt;/sql-query&gt;</programlisting>
+
+    <programlisting>List people = sess.getNamedQuery("persons")
+    .setString("namePattern", namePattern)
+    .setMaxResults(50)
+    .list();</programlisting>
+
+    <para>
+        Les éléments <literal>&lt;return-join&gt;</literal> et
+        <literal>&lt;load-collection&gt;</literal> sont respectivement utilisés pour lier
+        des associations et définir des requêtes qui initialisent des collections.
+    </para>
+
+    <programlisting>&lt;sql-query name="personsWith"&gt;
+    &lt;return alias="person" class="eg.Person"/&gt;
+    &lt;return-join alias="address" property="person.mailingAddress"/&gt;
+    SELECT person.NAME AS {person.name},
+           person.AGE AS {person.age},
+           person.SEX AS {person.sex},
+           address.STREET AS {address.street},
+           address.CITY AS {address.city},
+           address.STATE AS {address.state},
+           address.ZIP AS {address.zip}
+    FROM PERSON person
+    JOIN ADDRESS address
+        ON person.ID = address.PERSON_ID AND address.TYPE='MAILING'
+    WHERE person.NAME LIKE :namePattern
+&lt;/sql-query&gt;</programlisting>
+
+    <para>
+        Une requête SQL nommée peut retourner une valeur scalaire. Vous devez
+        spécifier l'alias de colonne et le type Hibernate utilisant l'élément
+        <literal>&lt;return-scalar&gt;</literal> :</para>
+
+    <programlisting>&lt;sql-query name="mySqlQuery"&gt;
+    &lt;return-scalar column="name" type="string"/&gt;
+    &lt;return-scalar column="age" type="long"/&gt;
+    SELECT p.NAME AS name,
+           p.AGE AS age,
+    FROM PERSON p WHERE p.NAME LIKE 'Hiber%'
+&lt;/sql-query&gt;</programlisting>
+
+    <para>
+        Vous pouvez externaliser les informations de mapping des résultats dans un
+        élément <literal>&lt;resultset&gt;</literal> pour soit les réutiliser
+        dans différentes requêtes nommées, soit à travers l'API
+        <literal>setResultSetMapping()</literal>.
+    </para>
+
+    <programlisting>&lt;resultset name="personAddress"&gt;
+    &lt;return alias="person" class="eg.Person"/&gt;
+    &lt;return-join alias="address" property="person.mailingAddress"/&gt;
+&lt;/resultset&gt;
+
+&lt;sql-query name="personsWith" resultset-ref="personAddress"&gt;
+    SELECT person.NAME AS {person.name},
+           person.AGE AS {person.age},
+           person.SEX AS {person.sex},
+           address.STREET AS {address.street},
+           address.CITY AS {address.city},
+           address.STATE AS {address.state},
+           address.ZIP AS {address.zip}
+    FROM PERSON person
+    JOIN ADDRESS address
+        ON person.ID = address.PERSON_ID AND address.TYPE='MAILING'
+    WHERE person.NAME LIKE :namePattern
+&lt;/sql-query&gt;</programlisting>
+
+    <sect2 id="propertyresults">
+      <title>Utilisation de return-property pour spécifier explicitement les noms des colonnes/alias</title>
+
+      <para>
+          Avec <literal>&lt;return-property&gt;</literal> vous pouvez explicitement dire
+          à Hibernate quels alias de colonne utiliser, plutot que d'employer la syntaxe
+          <literal>{}</literal> pour laisser Hibernate injecter ses propres alias.
+      </para>
+
+      <programlisting>&lt;sql-query name="mySqlQuery"&gt;
+    &lt;return alias="person" class="eg.Person"&gt;
+        &lt;return-property name="name" column="myName"/&gt;
+        &lt;return-property name="age" column="myAge"/&gt;
+        &lt;return-property name="sex" column="mySex"/&gt;
+    &lt;/return&gt;
+    SELECT person.NAME AS myName,
+           person.AGE AS myAge,
+           person.SEX AS mySex,
+    FROM PERSON person WHERE person.NAME LIKE :name
+&lt;/sql-query&gt;
+</programlisting>
+
+      <para>
+          <literal>&lt;return-property&gt;</literal> fonctionne aussi avec de
+          multiple colonnes. Cela résout une limitation de la syntaxe <literal>{}</literal>
+          qui ne peut pas permettre une bonne granularité des propriétés multi-colonnes.
+      </para>
+
+      <programlisting>&lt;sql-query name="organizationCurrentEmployments"&gt;
+    &lt;return alias="emp" class="Employment"&gt;
+        &lt;return-property name="salary"&gt;
+            &lt;return-column name="VALUE"/&gt;
+            &lt;return-column name="CURRENCY"/&gt;
+        &lt;/return-property&gt;
+        &lt;return-property name="endDate" column="myEndDate"/&gt;
+    &lt;/return&gt;
+        SELECT EMPLOYEE AS {emp.employee}, EMPLOYER AS {emp.employer},
+        STARTDATE AS {emp.startDate}, ENDDATE AS {emp.endDate},
+        REGIONCODE as {emp.regionCode}, EID AS {emp.id}, VALUE, CURRENCY
+        FROM EMPLOYMENT
+        WHERE EMPLOYER = :id AND ENDDATE IS NULL
+        ORDER BY STARTDATE ASC
+&lt;/sql-query&gt;</programlisting>
+
+      <para>
+          Notez que dans cet exemple nous avons utilisé <literal>&lt;return-property&gt;</literal>
+          en combinaison avec la syntaxe <literal>{}</literal> pour l'injection. Cela autorise les
+          utilisateurs à choisir comment ils veulent référencer les colonnes et les propriétés.
+      </para>
+
+      <para>
+          Si votre mapping a un discriminant vous devez utiliser
+          <literal>&lt;return-discriminator&gt;</literal> pour spécifier la colonne
+          discriminante.
+      </para>
+    </sect2>
+
+    <sect2 id="sp_query" revision="1">
+      <title>Utilisation de procédures stockées pour les requêtes</title>
+
+      <para>
+          Hibernate 3 introduit le support des requêtes via procédures stockées et les fonctions. 
+          La documentation suivante est valable pour les deux.
+          Les procédures stockées/fonctions doivent retourner l'ensemble de résultats en tant que
+          premier paramètre sortant (NdT: "out-parameter") pour être capable de fonctionner
+          avec Hibernate. Un exemple d'une telle procédure stockée en Oracle 9 et
+          version supérieure :
+      </para>
+
+      <programlisting>CREATE OR REPLACE FUNCTION selectAllEmployments
+    RETURN SYS_REFCURSOR
+AS
+    st_cursor SYS_REFCURSOR;
+BEGIN
+    OPEN st_cursor FOR
+ SELECT EMPLOYEE, EMPLOYER,
+ STARTDATE, ENDDATE,
+ REGIONCODE, EID, VALUE, CURRENCY
+ FROM EMPLOYMENT;
+      RETURN  st_cursor;
+ END;</programlisting>
+
+      <para>Pour utiliser cette requête dans Hibernate vous avez besoin de la mapper via une requête nommée.</para>
+
+      <programlisting>&lt;sql-query name="selectAllEmployees_SP" callable="true"&gt;
+    &lt;return alias="emp" class="Employment"&gt;
+        &lt;return-property name="employee" column="EMPLOYEE"/&gt;
+        &lt;return-property name="employer" column="EMPLOYER"/&gt;
+        &lt;return-property name="startDate" column="STARTDATE"/&gt;
+        &lt;return-property name="endDate" column="ENDDATE"/&gt;
+        &lt;return-property name="regionCode" column="REGIONCODE"/&gt;
+        &lt;return-property name="id" column="EID"/&gt;
+        &lt;return-property name="salary"&gt;
+            &lt;return-column name="VALUE"/&gt;
+            &lt;return-column name="CURRENCY"/&gt;
+        &lt;/return-property&gt;
+    &lt;/return&gt;
+    { ? = call selectAllEmployments() }
+&lt;/sql-query&gt;</programlisting>
+
+      <para>
+          Notez que les procédures stockées retournent, pour le moment, seulement des
+          scalaires et des entités. <literal>&lt;return-join&gt;</literal> et
+          <literal>&lt;load-collection&gt;</literal> ne sont pas supportés.
+      </para>
+
+      <sect3 id="querysql-limits-storedprocedures" revision="1">
+        <title>Règles/limitations lors de l'utilisation des procédures stockées</title>
+
+        <para>
+            Pur utiliser des procédures stockées avec Hibernate, les procédures doivent
+            suivre certaines règles. Si elles ne suivent pas ces règles, elles ne sont pas
+            utilisables avec Hibernate. Si vous voulez encore utiliser ces procédures vous
+            devez les exécuter via <literal>session.connection()</literal>. Les règles
+            sont différentes pour chaque base de données, puisque les vendeurs de base
+            de données ont des sémantiques/syntaxes différentes pour les procédures stockées.
+        </para>
+
+        <para>Les requêtes de procédures stockées ne peuvent pas être paginées avec
+            <literal>setFirstResult()/setMaxResults()</literal>.</para>
+
+        <para>Pour Oracle les règles suivantes s'appliquent :</para>
+
+        <itemizedlist spacing="compact">
+          <listitem>
+            <para>
+                La procédure doit retourner un ensemble de résultats. Le
+                prmeier paramètre d'une procédure doit être un <literal>OUT</literal> 
+                qui retourne un ensemble de résultats. Ceci est fait en
+                retournant un <literal>SYS_REFCURSOR</literal> dans Oracle 9 ou 10. Dans
+                Oracle vous avez besoin de définir un type <literal>REF CURSOR</literal>.</para>
+          </listitem>
+
+        </itemizedlist>
+
+        <para>Pour Sybase ou MS SQL server les règles suivantes s'appliquent :</para>
+
+        <itemizedlist spacing="compact">
+          <listitem>
+            <para>La procédure doit retourner un ensemble de résultats. Notez que comme
+            ces serveurs peuvent retourner de multiples ensembles de résultats et mettre à jour
+            des compteurs, Hibernate itérera les résultats et prendra le premier résultat qui est
+            un ensemble de résultat comme valeur de retour. Tout le reste sera ignoré.</para>
+          </listitem>
+
+          <listitem>
+            <para>Si vous pouvez activer <literal>SET NOCOUNT ON</literal> dans votre procédure,
+                elle sera probablement plus efficace, mais ce n'est pas une obligation.</para>
+          </listitem>
+        </itemizedlist>
+      </sect3>
+    </sect2>
+  </sect1>
+
+  <sect1 id="querysql-cud">
+    <title>SQL personnalisé pour créer, mettre à jour et effacer</title>
+
+    <para>
+        Hibernate3 peut utiliser des expression SQL personnalisées pour des opérations de création,
+        de mise à jour, et de suppression. Les objets persistants les classes et les collections
+        dans Hibernate contiennent déjà un ensemble de chaînes de caractères générées lors de la
+        configuration (insertsql, deletesql, updatesql, etc). Les tages de mapping
+    <literal>&lt;sql-insert&gt;</literal>,
+    <literal>&lt;sql-delete&gt;</literal>, et
+    <literal>&lt;sql-update&gt;</literal> surchargent ces chaînes de caractères :</para>
+
+    <programlisting>&lt;class name="Person"&gt;
+    &lt;id name="id"&gt;
+        &lt;generator class="increment"/&gt;
+    &lt;/id&gt;
+    &lt;property name="name" not-null="true"/&gt;
+    &lt;sql-insert&gt;INSERT INTO PERSON (NAME, ID) VALUES ( UPPER(?), ? )&lt;/sql-insert&gt;
+    &lt;sql-update&gt;UPDATE PERSON SET NAME=UPPER(?) WHERE ID=?&lt;/sql-update&gt;
+    &lt;sql-delete&gt;DELETE FROM PERSON WHERE ID=?&lt;/sql-delete&gt;
+&lt;/class&gt;</programlisting>
+
+    <para>Le SQL est directement exécuté dans votre base de données, donc vous êtes libre d'utiliser
+        le dialecte que vous souhaitez. Cela réduira bien sûr la portabilité de votre mapping si vous
+        utilisez du SQL spécifique à votre base de données.</para>
+
+    <para>Les procédures stockées sont supportées si l'attribut <literal>callable</literal> est paramétré :</para>
+
+    <programlisting>&lt;class name="Person"&gt;
+    &lt;id name="id"&gt;
+        &lt;generator class="increment"/&gt;
+    &lt;/id&gt;
+    &lt;property name="name" not-null="true"/&gt;
+    &lt;sql-insert callable="true"&gt;{call createPerson (?, ?)}&lt;/sql-insert&gt;
+    &lt;sql-delete callable="true"&gt;{? = call deletePerson (?)}&lt;/sql-delete&gt;
+    &lt;sql-update callable="true"&gt;{? = call updatePerson (?, ?)}&lt;/sql-update&gt;
+&lt;/class&gt;</programlisting>
+
+    <para>L'ordre des paramètres positionnels est actuellement vital, car ils doivent être dans la
+        même séquence qu'Hibernate les attend.</para>
+
+    <para>
+        Vous pouvez voir l'ordre attendu en activant les journaux de debug pour le
+        niveau <literal>org.hibernate.persister.entity</literal> level. Avec ce niveau activé,
+        Hibernate imprimera le SQL statique qui est utilisé pour créer, mettre à jour,
+        supprimer, etc. des entités. (Pour voir la séquence attendue, rappelez-vous de ne pas
+        inclure votre SQL personnalisé dans les fichiers de mapping de manière à surcharger le
+        SQL statique généré par Hibernate.)</para>
+
+    <para>Les procédures stockées sont dans la plupart des cas (lire : il vaut mieux le faire)
+    requises pour retourner le nombre de lignes insérées/mises à jour/supprimées, puisque
+    Hibernate fait quelques vérifications de succès lors de l'exécution de l'expression.
+    Hibernate inscrit toujours la première expression comme un paramètre de sortie numérique pour les
+    opérations CUD :</para>
+
+    <programlisting>CREATE OR REPLACE FUNCTION updatePerson (uid IN NUMBER, uname IN VARCHAR2)
+    RETURN NUMBER IS
+BEGIN
+
+    update PERSON
+    set
+        NAME = uname,
+    where
+        ID = uid;
+
+    return SQL%ROWCOUNT;
+
+END updatePerson;</programlisting>
+  </sect1>
+
+  <sect1 id="querysql-load">
+    <title>SQL personnalisé pour le chargement</title>
+
+    <para>Vous pouvez aussi déclarer vos propres requêtes SQL (ou HQL) pour le chargement d'entité :</para>
+
+    <programlisting>&lt;sql-query name="person"&gt;
+    &lt;return alias="pers" class="Person" lock-mode="upgrade"/&gt;
+    SELECT NAME AS {pers.name}, ID AS {pers.id}
+    FROM PERSON
+    WHERE ID=?
+    FOR UPDATE
+&lt;/sql-query&gt;</programlisting>
+
+    <para>Ceci est juste une déclaration de requête nommée, comme vu plus tôt. Vous pouvez référencer
+    cette requête nommée dans un mapping de classe :</para>
+
+    <programlisting>&lt;class name="Person"&gt;
+    &lt;id name="id"&gt;
+        &lt;generator class="increment"/&gt;
+    &lt;/id&gt;
+    &lt;property name="name" not-null="true"/&gt;
+    &lt;loader query-ref="person"/&gt;
+&lt;/class&gt;</programlisting>
+
+    <para>Ceci fonctionne même avec des procédures stockées.</para>
+
+    <para>Vous pouvez même définir une requête pour le chargement d'une collection :</para>
+
+    <programlisting>&lt;set name="employments" inverse="true"&gt;
+    &lt;key/&gt;
+    &lt;one-to-many class="Employment"/&gt;
+    &lt;loader query-ref="employments"/&gt;
+&lt;/set&gt;</programlisting>
+
+    <programlisting>&lt;sql-query name="employments"&gt;
+    &lt;load-collection alias="emp" role="Person.employments"/&gt;
+    SELECT {emp.*}
+    FROM EMPLOYMENT emp
+    WHERE EMPLOYER = :id
+    ORDER BY STARTDATE ASC, EMPLOYEE ASC
+&lt;/sql-query&gt;</programlisting>
+
+    <para>Vous pourriez même définir un chargeur d'entité qui charge une collection par jointure :</para>
+
+    <programlisting>&lt;sql-query name="person"&gt;
+    &lt;return alias="pers" class="Person"/&gt;
+    &lt;return-join alias="emp" property="pers.employments"/&gt;
+    SELECT NAME AS {pers.*}, {emp.*}
+    FROM PERSON pers
+    LEFT OUTER JOIN EMPLOYMENT emp
+        ON pers.ID = emp.PERSON_ID
+    WHERE ID=?
+&lt;/sql-query&gt;</programlisting>
+  </sect1>
+</chapter>
\ No newline at end of file

Copied: core/trunk/documentation/manual/fr-FR/src/main/docbook/content/session_api.xml (from rev 14070, core/trunk/documentation/manual/fr-FR/src/main/docbook/modules/session_api.xml)
===================================================================
--- core/trunk/documentation/manual/fr-FR/src/main/docbook/content/session_api.xml	                        (rev 0)
+++ core/trunk/documentation/manual/fr-FR/src/main/docbook/content/session_api.xml	2007-10-09 18:28:36 UTC (rev 14074)
@@ -0,0 +1,1226 @@
+<?xml version="1.0" encoding="ISO-8859-1"?>
+<chapter id="objectstate">
+    <title>Travailler avec des objets</title>
+    <para>
+        Hibernate est une solution de mapping objet/relationnel complète qui ne masque pas
+        seulement au développpeur les détails du système de gestion de base de données sous-jacent,
+        mais offre aussi <emphasis>la gestion d'état</emphasis> des objets. C'est, contrairement
+        à la gestion de <literal>statements</literal> SQL dans les couches de persistance
+        habituelles JDBC/SQL, une vue orientée objet très naturelle de la persistance dans les
+        applications Java.
+    </para>
+
+	<para>
+        En d'autres mots, les développeurs d'applications Hibernate devrait toujours
+        réfléchir à <emphasis>l'état</emphasis> de leurs objets, et pas nécessairement à
+        l'exécution des expressions SQL. Cette part est prise en charge pas Hibernate et
+        seulement importante pour les développeurs d'applications lors du réglage de la
+        performance de leur système.
+    </para>
+
+    <sect1 id="objectstate-overview">
+        <title>États des objets Hibernate</title>
+
+        <para>
+            Hibernate définit et comprend les états suivants :
+        </para>
+
+        <itemizedlist>
+            <listitem>
+                <para>
+                    <emphasis>Éphémère</emphasis> (NdT : transient) - un objet est éphémère s'il a juste
+                    été instancié en utilisant l'opérateur <literal>new</literal>. Il n'a aucune
+                    représentation persistante dans la base de données et aucune valeur d'identifiant
+                    n'a été assignée. Les instances éphémères seront détruites par le ramasse-miettes
+                    si l'application n'en conserve aucune référence. Utilisez la <literal>Session</literal>
+                    d'Hibernate pour rendre un objet persistant (et laisser Hibernate s'occuper des
+                    expressions SQL qui ont besoin d'être exécutées pour cette transistion).
+                </para>
+            </listitem>
+            <listitem>
+                <para>
+                    <emphasis>Persistant</emphasis> - une instance persistante a une représentation dans la
+                    base de données et une valeur d'identifiant. Elle pourrait avoir juste été sauvegardée
+                    ou chargée, pourtant, elle est par définition dans la portée d'une <literal>Session</literal>.
+                    Hibernate détectera n'importe quels changements effectués sur un objet dans l'état
+                    persistant et synchronisera l'état avec la base de données lors de la fin l'unité de travail.
+                    Les développeurs n'exécutent pas d'expressions <literal>UPDATE</literal> ou
+                    <literal>DELETE</literal> manuelles lorsqu'un objet devrait être rendu éphémère.
+                </para>
+            </listitem>
+            <listitem>
+                <para>
+                    <emphasis>Détaché</emphasis> - une instance détachée est un objet qui a été persistant,
+                    mais dont sa <literal>Session</literal> a été fermée. La référence à l'objet est
+                    encore valide, bien sûr, et l'instance détachée pourrait même être modifiée dans cet
+                    état. Une instance détachée peut être réattachée à une nouvelle <literal>Session</literal>
+                    plus tard dans le temps, la rendant (et toutes les modifications avec) de nouveau persistante.
+                    Cette fonctionnalité rend possible un modèle de programmation pour de longues unités de travail
+                    qui requièrent un temps de réflexion de l'utilisateur. Nous les appelons des <emphasis>conversations</emphasis>,
+                    c'est-à-dire une unité de travail du point de vue de l'utilisateur.
+                </para>
+            </listitem>
+        </itemizedlist>
+
+        <para>
+            Nous alons maintenant dicuster des états et des transitions d'état (et des méthodes
+            d'Hibernate qui déclenchent une transition) plus en détails.
+        </para>
+
+    </sect1>
+
+    <sect1 id="objectstate-makingpersistent" revision="1">
+        <title>Rendre des objets persistants</title>
+
+        <para>
+            Les instances nouvellement instanciées d'une classe persistante sont considérées
+            <emphasis>éphémères</emphasis> par Hibernate. Nous pouvons rendre une instance
+            éphémère <emphasis>persistante</emphasis> en l'associant avec une session :
+        </para>
+
+        <programlisting><![CDATA[DomesticCat fritz = new DomesticCat();
+fritz.setColor(Color.GINGER);
+fritz.setSex('M');
+fritz.setName("Fritz");
+Long generatedId = (Long) sess.save(fritz);]]></programlisting>
+
+        <para>
+            Si <literal>Cat</literal> a un identifiant généré, l'identifiant est généré et assigné
+            au <literal>cat</literal> lorsque <literal>save()</literal> est appelée. Si <literal>Cat</literal>
+            a un identifiant <literal>assigned</literal>, ou une clef composée, l'identifiant
+            devrait être assigné à l'instance de <literal>cat</literal> avant d'appeler <literal>save()</literal>.
+            Vous pouvez aussi utiliser <literal>persist()</literal> à la place de<literal>save()</literal>,
+            avec la sémantique définie plus tôt dans le brouillon d'EJB3.
+        </para>
+
+        <para>
+            Alternativement, vous pouvez assigner l'identifiant en utilisant une version
+            surchargée de <literal>save()</literal>.
+        </para>
+
+<programlisting><![CDATA[DomesticCat pk = new DomesticCat();
+pk.setColor(Color.TABBY);
+pk.setSex('F');
+pk.setName("PK");
+pk.setKittens( new HashSet() );
+pk.addKitten(fritz);
+sess.save( pk, new Long(1234) );]]></programlisting>
+
+        <para>
+            Si l'objet que vous rendez persistant a des objets associés (par exemple,
+            la collection <literal>kittens</literal> dans l'exemple précédent), ces objets
+            peuvent être rendus persistants dans n'importe quel ordre que vous souhaitez
+            à moins que vous ayez une contrainte <literal>NOT NULL</literal> sur la
+            colonne de la clef étrangère. Il n'y a jamais de risque de violer une
+            contrainte de clef étrangère. Cependant, vous pourriez violer une contrainte
+            <literal>NOT NULL</literal> si vous appeliez <literal>save()</literal> sur
+            les objets dans le mauvais ordre.
+        </para>
+
+        <para>
+            Habituellement, vous ne vous préoccupez pas de ce détail, puisque vous
+            utiliserez très probablement la fonctionnalité de <emphasis>persistance
+            transitive</emphasis> d'Hibernate pour sauvegarder les objets associés
+            automatiquement. Alors, même les violations de contrainte <literal>NOT NULL</literal>
+            n'ont plus lieu - Hibernate prendra soin de tout. La persistance transitive est
+            traitée plus loin dans ce chapitre.
+        </para>
+
+    </sect1>
+
+    <sect1 id="objectstate-loading">
+        <title>Chargement d'un objet</title>
+
+        <para>
+            Les méthodes <literal>load()</literal> de <literal>Session</literal> vous donnent
+            un moyen de récupérer une instance persistante si vous connaissez déjà son identifiant.
+            <literal>load()</literal> prend un objet de classe et chargera l'état dans une instance
+            nouvellement instanciée de cette classe, dans un état persistant.
+        </para>
+
+        <programlisting><![CDATA[Cat fritz = (Cat) sess.load(Cat.class, generatedId);]]></programlisting>
+
+<programlisting><![CDATA[// vous avez besoin d'envelopper les identiants primitifs
+long pkId = 1234;
+DomesticCat pk = (DomesticCat) sess.load( Cat.class, new Long(pkId) );]]></programlisting>
+
+        <para>
+            Alternativement, vous pouvez charger un état dans une instance donnée :
+        </para>
+
+<programlisting><![CDATA[Cat cat = new DomesticCat();
+// load pk's state into cat
+sess.load( cat, new Long(pkId) );
+Set kittens = cat.getKittens();]]></programlisting>
+
+        <para>
+            Notez que <literal>load()</literal> lèvera une exception irrécupérable s'il
+            n'y a pas de ligne correspondante dans la base de données. Si la classe est mappée
+            avec un proxy, <literal>load()</literal> retourne juste un proxy non initialisé et
+            n'accède en fait pas à la base de données jusqu'à ce que vous invoquiez une
+            méthode du proxy. Ce comportement est très utile si vous souhaitez créer
+            une association vers un objet sans réellement le charger à partir de la base de
+            données. Cela permet aussi à de multiples instances d'être chargées comme un lot
+            si <literal>batch-size</literal> est défini pour le mapping de la classe.
+        </para>
+
+        <para>
+            Si vous n'êtes pas certain qu'une ligne correspondante existe, vous devriez
+            utiliser la méthode <literal>get()</literal>, laquelle accède à la base de
+            données immédiatement et retourne null s'il n'y a pas de ligne correspondante.
+        </para>
+
+        <programlisting><![CDATA[Cat cat = (Cat) sess.get(Cat.class, id);
+if (cat==null) {
+    cat = new Cat();
+    sess.save(cat, id);
+}
+return cat;]]></programlisting>
+
+        <para>
+            Vous pouvez même charger un objet en employant un <literal>SELECT ... FOR UPDATE</literal> SQL,
+            en utilisant un <literal>LockMode</literal>. Voir la documentation de l'API pour plus d'informations.
+        </para>
+
+        <programlisting><![CDATA[Cat cat = (Cat) sess.get(Cat.class, id, LockMode.UPGRADE);]]></programlisting>
+
+        <para>
+            Notez que n'importe quelles instances associées ou collections contenues
+            <emphasis>ne sont pas</emphasis> sélectionnées par <literal>FOR UPDATE</literal>,
+            à moins que vous ne décidiez de spécifier <literal>lock</literal> ou <literal>all</literal>
+            en tant que style de cascade pour l'association.
+        </para>
+
+        <para>
+            Il est possible de re-charger un objet et toutes ses collections à n'importe quel moment,
+            en utilisant la méthode <literal>refresh()</literal>. C'est utile lorsque des "triggers" de
+            base de données sont utilisés pour initiliser certains propriétés de l'objet.
+        </para>
+
+        <programlisting><![CDATA[sess.save(cat);
+sess.flush(); //force the SQL INSERT
+sess.refresh(cat); //re-read the state (after the trigger executes)]]></programlisting>
+
+        <para>
+            Une question importante apparaît généralement à ce point : combien (NdT : de données) Hibernate
+            charge-t-il de la base de données et combient de <literal>SELECT</literal>s utilisera-t-il ?
+            Cela dépent de la <emphasis>stratégie de récupération</emphasis> et cela est expliqué dans
+            <xref linkend="performance-fetching"/>.
+        </para>
+
+    </sect1>
+
+    <sect1 id="objectstate-querying" revision="1">
+        <title>Requêtage</title>
+
+        <para>
+            Si vous ne connaissez par les identifiants des objets que vous recherchez, vous
+            avez besoin d'une requête. Hibernate supporte un langage de requêtes orientées objet
+            facile à utiliser mais puissant. Pour la création de requêtes par programmation,
+            Hibernate supporte une fonction de requêtage sophistiqué Criteria et Example (QBC et QBE).
+            Vous pouvez aussi exprimez votre requête dans le SQL natif de votre base de données,
+            avec un support optionnel d'Hibernate pour la conversion des ensembles de résultats en
+            objets.
+        </para>
+
+        <sect2 id="objectstate-querying-executing">
+            <title>Exécution de requêtes</title>
+
+            <para>
+                Les requêtes HQL et SQL natives sont représentées avec une instance de <literal>org.hibernate.Query</literal>.
+                L'interface offre des méthodes pour la liaison des paramètres, la gestion des ensembles de resultats, et pour
+                l'exécution de la requête réelle. Vous obtenez toujours une <literal>Query</literal> en utilisant la
+                <literal>Session</literal> courante :
+            </para>
+
+        <programlisting><![CDATA[List cats = session.createQuery(
+    "from Cat as cat where cat.birthdate < ?")
+    .setDate(0, date)
+    .list();
+
+List mothers = session.createQuery(
+    "select mother from Cat as cat join cat.mother as mother where cat.name = ?")
+    .setString(0, name)
+    .list();
+
+List kittens = session.createQuery(
+    "from Cat as cat where cat.mother = ?")
+    .setEntity(0, pk)
+    .list();
+
+Cat mother = (Cat) session.createQuery(
+    "select cat.mother from Cat as cat where cat = ?")
+    .setEntity(0, izi)
+    .uniqueResult();]]></programlisting>
+
+            <para>
+                Une requête est généralement exécutée en invoquant <literal>list()</literal>,
+                le résultat de la requête sera chargée complètement dans une collection en mémoire.
+                Les intances d'entités recupérées par une requête sont dans un état persistant.
+                La méthode <literal>uniqueResult()</literal> offre un raccourci si vous
+                savez que votre requête retournera seulement un seul objet.
+            </para>
+
+            <sect3 id="objectstate-querying-executing-iterate">
+                <title>Itération de résultats</title>
+
+                <para>
+                    Occasionnellement, vous pourriez être capable d'obtenir de meilleures
+                    performances en exécutant la requête avec la méthode <literal>iterate()</literal>.
+                    Ce sera généralement seulement le cas si vous espérez que les intances réelles
+                    d'entité retournées par la requête soient déjà chargées dans la session ou le
+                    cache de second niveau. Si elles ne sont pas cachées, <literal>iterate()</literal>
+                    sera plus lent que <literal>list()</literal> et pourrait nécessiter plusieurs
+                    accès à la base de données pour une simple requête, généralement <emphasis>1</emphasis>
+                    pour le select initial qui retourne seulement les identifiants, et <emphasis>n</emphasis>
+                    selects supplémentaires pour initialiser les instances réelles.
+                </para>
+
+                <programlisting><![CDATA[// fetch ids
+Iterator iter = sess.createQuery("from eg.Qux q order by q.likeliness").iterate();
+while ( iter.hasNext() ) {
+    Qux qux = (Qux) iter.next();  // fetch the object
+    // something we couldnt express in the query
+    if ( qux.calculateComplicatedAlgorithm() ) {
+        // delete the current instance
+        iter.remove();
+        // dont need to process the rest
+        break;
+    }
+}]]></programlisting>
+            </sect3>
+
+            <sect3 id="objectstate-querying-executing-tuples">
+                <title>Requêtes qui retournent des tuples</title>
+
+                <para>
+                    Les requêtes d'Hibernate retournent parfois des tuples d'objets, auquel cas chaque tuple
+                    est retourné comme un tableau :
+                </para>
+
+                <programlisting><![CDATA[Iterator kittensAndMothers = sess.createQuery(
+            "select kitten, mother from Cat kitten join kitten.mother mother")
+            .list()
+            .iterator();
+
+while ( kittensAndMothers.hasNext() ) {
+    Object[] tuple = (Object[]) kittensAndMothers.next();
+    Cat kitten = (Cat) tuple[0];
+    Cat mother = (Cat) tuple[1];
+    ....
+}]]></programlisting>
+
+            </sect3>
+
+            <sect3 id="objectstate-querying-executing-scalar"  revision="1">
+                <title>Résultats scalaires</title>
+
+                <para>
+                    Des requêtes peuvent spécifier une propriété d'une classe dans la clause <literal>select</literal>.
+                    Elles peuvent même appeler des fonctions d'aggrégat SQL. Les propriétés ou les aggrégats sont
+                    considérés comme des résultats "scalaires" (et pas des entités dans un état persistant).
+                </para>
+
+                <programlisting><![CDATA[Iterator results = sess.createQuery(
+        "select cat.color, min(cat.birthdate), count(cat) from Cat cat " +
+        "group by cat.color")
+        .list()
+        .iterator();
+
+while ( results.hasNext() ) {
+    Object[] row = (Object[]) results.next();
+    Color type = (Color) row[0];
+    Date oldest = (Date) row[1];
+    Integer count = (Integer) row[2];
+    .....
+}]]></programlisting>
+
+            </sect3>
+
+            <sect3 id="objectstate-querying-executing-parameters">
+                <title>Lier des paramètres</title>
+
+                <para>
+                    Des méthodes de <literal>Query</literal> sont fournies pour lier des
+                    valeurs à des paramètres nommés ou à des paramètres de style JDBC <literal>?</literal>.
+                    <emphasis>Contrairement à JDBC, les numéros des paramètres d'Hibernate commencent à zéro.</emphasis>
+                    Les paramètres nommés sont des identifiants de la forme <literal>:nom</literal> dans la chaîne de
+                    caractères de la requête. Les avantages des paramètres nommés sont :
+                </para>
+
+                <itemizedlist spacing="compact">
+                    <listitem>
+                        <para>
+                            les paramètres nommés sont insensibles à l'ordre de leur place dans la chaîne
+                            de la requête
+                        </para>
+                    </listitem>
+                    <listitem>
+                        <para>
+                            ils peuvent apparaître plusieurs fois dans la même requête
+                        </para>
+                    </listitem>
+                    <listitem>
+                        <para>
+                            ils sont auto-documentés
+                        </para>
+                    </listitem>
+                </itemizedlist>
+
+                <programlisting><![CDATA[//paramètre nomme (préféré)
+Query q = sess.createQuery("from DomesticCat cat where cat.name = :name");
+q.setString("name", "Fritz");
+Iterator cats = q.iterate();]]></programlisting>
+
+                <programlisting><![CDATA[//paramètre positionnel
+Query q = sess.createQuery("from DomesticCat cat where cat.name = ?");
+q.setString(0, "Izi");
+Iterator cats = q.iterate();]]></programlisting>
+
+                <programlisting><![CDATA[//liste de paramètres nommés
+List names = new ArrayList();
+names.add("Izi");
+names.add("Fritz");
+Query q = sess.createQuery("from DomesticCat cat where cat.name in (:namesList)");
+q.setParameterList("namesList", names);
+List cats = q.list();]]></programlisting>
+
+            </sect3>
+
+            <sect3 id="objectstate-querying-executing-pagination">
+                <title>Pagination</title>
+
+                <para>
+                    Si vous avez besoin de spécifier des liens sur votre ensemble de résultats (le nombre
+                    maximum de lignes que vous voulez récupérez et/ou la première ligne que vous voulez récupérer)
+                    vous devriez utiliser des méthodes de l'interface <literal>Query</literal> :
+                </para>
+
+                <programlisting><![CDATA[Query q = sess.createQuery("from DomesticCat cat");
+q.setFirstResult(20);
+q.setMaxResults(10);
+List cats = q.list();]]></programlisting>
+
+                <para>
+                    Hibernate sait comment traduite cette requête de limite en SQL natif pour votre SGBD.
+                </para>
+
+            </sect3>
+
+            <sect3 id="objectstate-querying-executing-scrolling">
+                <title>Itération "scrollable"</title>
+
+                <para>
+                    Si votre connecteur JDBC supporte les <literal>ResultSet</literal>s "scrollables",
+                    l'interface <literal>Query</literal> peut être utilisée pour obtenir un objet
+                    <literal>ScrollableResults</literal>, lequel permet une navigation flexible dans les
+                    résultats de la requête.
+                </para>
+
+                <programlisting><![CDATA[Query q = sess.createQuery("select cat.name, cat from DomesticCat cat " +
+                            "order by cat.name");
+ScrollableResults cats = q.scroll();
+if ( cats.first() ) {
+
+    // trouve le premier nom sur chaque page d'une liste alphabétique de noms de chats
+    firstNamesOfPages = new ArrayList();
+    do {
+        String name = cats.getString(0);
+        firstNamesOfPages.add(name);
+    }
+    while ( cats.scroll(PAGE_SIZE) );
+
+    // Maintenant, obtiens la première page de chats
+    pageOfCats = new ArrayList();
+    cats.beforeFirst();
+    int i=0;
+    while( ( PAGE_SIZE > i++ ) && cats.next() ) pageOfCats.add( cats.get(1) );
+
+}
+cats.close()]]></programlisting>
+
+                <para>
+                    Notez qu'une connexion ouverte (et un curseur) est requise pour cette fonctionnalité,
+                    utilisez <literal>setMaxResult()</literal>/<literal>setFirstResult()</literal> si vous
+                    avez besoin d'une fonctionnalité de pagination hors ligne.
+                </para>
+
+            </sect3>
+
+            <sect3 id="objectstate-querying-executing-named">
+                <title>Externaliser des requêtes nommées</title>
+
+                <para>
+                    Vous pouvez aussi définir des requêtes nommées dans le document de mapping.
+                    (Souvenez-vous d'utiliser une section <literal>CDATA</literal> si votre requête
+                    contient des caractères qui pourraient être interprétés comme des éléments XML.)
+                </para>
+
+                <programlisting><![CDATA[<query name="eg.DomesticCat.by.name.and.minimum.weight"><![CDATA[
+    from eg.DomesticCat as cat
+        where cat.name = ?
+        and cat.weight > ?
+] ]></query>]]></programlisting>
+
+                <para>
+                    La liaison de paramètres et l'exécution sont fait par programmation :
+                </para>
+
+                <programlisting><![CDATA[Query q = sess.getNamedQuery("eg.DomesticCat.by.name.and.minimum.weight");
+q.setString(0, name);
+q.setInt(1, minWeight);
+List cats = q.list();]]></programlisting>
+
+                <para>
+                    Notez que le code réel du programme est indépendant du langage de requête qui est
+                    utilisé, vous pouvez aussi définir des requêtes SQL nativez dans les méta-données, ou
+                    migrer des requêtes existantes vers Hibernate en les plaçant dans les fichiers de mapping.
+                </para>
+
+            </sect3>
+
+        </sect2>
+
+        <sect2 id="objectstate-filtering" revision="1">
+            <title>Filtrer des collections</title>
+            <para>
+                Un <emphasis>filtre</emphasis> de collection est un type spécial de requête qui peut être
+                appliqué à une collection persistante ou à un tableau. La chaîne de requête peut se référer à
+                <literal>this</literal>, correspondant à l'élément de la collection courant.
+            </para>
+
+            <programlisting><![CDATA[Collection blackKittens = session.createFilter(
+    pk.getKittens(),
+    "where this.color = ?")
+    .setParameter( Color.BLACK, Hibernate.custom(ColorUserType.class) )
+    .list()
+);]]></programlisting>
+
+            <para>
+                La collection retournée est considérée comme un bag, et c'est une copie de la
+                collection donnée. La collection originale n'est pas modifiée (c'est contraire
+                à l'implication du nom "filtre"; mais cohérent avec le comportement attendu).
+            </para>
+
+            <para>
+                Observez que les filtres ne nécessitent pas une clause <literal>from</literal> (bien qu'ils
+                puissent en avoir une si besoin est). Les filtres ne sont pas limités à retourner des
+                éléments de la collection eux-mêmes.
+            </para>
+
+            <programlisting><![CDATA[Collection blackKittenMates = session.createFilter(
+    pk.getKittens(),
+    "select this.mate where this.color = eg.Color.BLACK.intValue")
+    .list();]]></programlisting>
+
+            <para>
+                Même une requête de filtre vide est utile, par exemple pour charger un sous-ensemble
+                d'éléments dans une énorme collection :
+            </para>
+
+            <programlisting><![CDATA[Collection tenKittens = session.createFilter(
+    mother.getKittens(), "")
+    .setFirstResult(0).setMaxResults(10)
+    .list();]]></programlisting>
+
+        </sect2>
+
+        <sect2 id="objecstate-querying-criteria" revision="1">
+           <title>Requêtes Criteria</title>
+
+            <para>
+                HQL est extrêmement puissant mais certains développeurs préfèrent construire des
+                requêtes dynamiquement, en utilisant l'API orientée objet, plutôt que construire
+                des chaînes de requêtes. Hibernate fournit une API intuitive de requête <literal>Criteria</literal>
+                pour ces cas :
+            </para>
+
+            <programlisting><![CDATA[Criteria crit = session.createCriteria(Cat.class);
+crit.add( Restrictions.eq( "color", eg.Color.BLACK ) );
+crit.setMaxResults(10);
+List cats = crit.list();]]></programlisting>
+
+            <para>
+                Les APIs <literal>Criteria</literal> et <literal>Example</literal> associé sont
+                traitées plus en détail dans <xref linkend="querycriteria"/>.
+            </para>
+
+        </sect2>
+
+        <sect2 id="objectstate-querying-nativesql" revision="2">
+            <title>Requêtes en SQL natif</title>
+
+            <para>
+                Vous pouvez exprimer une requête en SQL, en utilisant <literal>createSQLQuery()</literal>
+                et laisser Hibernate s'occuper du mapping des résultats vers des objets. Notez que vous
+                pouvez n'importe quand appeler <literal>session.connection()</literal> et utiliser
+                directement la <literal>Connection</literal> JDBC. Si vous choisissez d'utiliser
+                l'API Hibernate, vous devez mettre les alias SQL entre accolades :
+            </para>
+
+            <programlisting><![CDATA[List cats = session.createSQLQuery("SELECT {cat.*} FROM CAT {cat} WHERE ROWNUM<10")
+    .addEntity("cat", Cat.class)
+.list();]]></programlisting>
+                
+            <programlisting><![CDATA[List cats = session.createSQLQuery(
+    "SELECT {cat}.ID AS {cat.id}, {cat}.SEX AS {cat.sex}, " +
+           "{cat}.MATE AS {cat.mate}, {cat}.SUBCLASS AS {cat.class}, ... " +
+    "FROM CAT {cat} WHERE ROWNUM<10")
+    .addEntity("cat", Cat.class)
+.list()]]></programlisting>
+
+            <para>
+                Les requêtes SQL peuvent contenir des paramètres nommés et positionnels, comme des
+                requêtes Hibernate. Plus d'informations à propos des requêtes SQL natives dans Hibernate
+                peuvent être trouvées dans <xref linkend="querysql"/>.
+            </para>
+
+        </sect2>
+
+    </sect1>
+
+    <sect1 id="objectstate-modifying" revision="1">
+        <title>Modifier des objets persistants</title>
+
+        <para>
+            Les <emphasis>instances persistantes transactionnelles</emphasis> (c'est-à-dire des objets
+            chargés, sauvegardés, créés ou requêtés par la <literal>Session</literal>) peuvent être
+            manipulées par l'application et n'importe quel changement vers l'état persistant sera
+            persisté lorsque la <literal>Session</literal> est <emphasis>"flushée"</emphasis> (traité
+            plus tard dans ce chapitre). Il n'y a pas besoin d'appeler une méthode particulière
+            (comme <literal>update()</literal>, qui a un but différent) pour rendre vos modifications
+            persistantes. Donc la manière la plus directe de mettre à jour l'état d'un objet est de
+            le charger avec <literal>load()</literal>, et puis le manipuler directement, tant que la
+            <literal>Session</literal> est ouverte :
+        </para>
+
+        <programlisting><![CDATA[DomesticCat cat = (DomesticCat) sess.load( Cat.class, new Long(69) );
+cat.setName("PK");
+sess.flush();  // changes to cat are automatically detected and persisted]]></programlisting>
+
+        <para>
+            Parfois ce modèle de programmation est inefficace puisqu'il nécessiterait un
+            <literal>SELECT</literal> SQL (pour charger l'objet) et un <literal>UPDATE</literal>
+            SQL (pour persister son état mis à jour) dans la même session. Aussi Hibernate offre
+            une autre approche, en utilisant des instances détachées.
+        </para>
+
+        <para>
+            <emphasis>Notez que Hibernate n'offre par sa propre API pour l'exécution directe
+            d'expressions <literal>UPDATE</literal> ou <literal>DELETE</literal>. Hibernate
+            est un service de <emphasis>gestion d'état</emphasis>, vous n'avez pas à penser
+            aux <emphasis>expressions</emphasis> pour l'utiliser. JDBC est une API parfaite
+            pour exécuter des expressions SQL, vous pouvez obtenir une <literal>Connection</literal>
+            JDBC n'importe quand en appelant <literal>session.connection()</literal>. En outre,
+            la notion d'opérations de masse entre en conflit avec le mapping objet/relationnel
+            pour les applications orientées processus de transactions en ligne. Les futures
+            versions d'Hibernate peuvent cependant fournir des fonctions d'opération de masse.
+            Voir <xref linkend="batch"/> pour les astuces possibles d'opérations groupées.</emphasis>
+        </para>
+
+    </sect1>
+
+    <sect1 id="objectstate-detached" revision="2">
+        <title>Modifier des objets détachés</title>
+
+        <para>
+            Beaucoup d'applications ont besoin de récupérer un objet dans une transaction,
+            l'envoyer à la couche interfacée avec l'utilisateur pour les manipulations, puis
+            sauvegarder les changements dans une nouvelle transaction. Les applications
+            qui utilisent cette approche dans un environnement à haute concurrence utilisent
+            généralement des données versionnées pour assurer l'isolation pour les "longues"
+            unités de travail.
+        </para>
+
+        <para>
+            Hibernate supporte ce modèle en permettant pour le réattachement d'instances détachées
+            l'utilisation des méthodes <literal>Session.update()</literal> ou <literal>Session.merge()</literal> :
+        </para>
+
+        <programlisting><![CDATA[// dans la première session
+Cat cat = (Cat) firstSession.load(Cat.class, catId);
+Cat potentialMate = new Cat();
+firstSession.save(potentialMate);
+
+// dans une couche plus haute de l'application
+cat.setMate(potentialMate);
+
+// plus tard, dans une nouvelle session
+secondSession.update(cat);  // update cat
+secondSession.update(mate); // update mate]]></programlisting>
+
+        <para>
+            Si le <literal>Cat</literal> avec l'identifiant <literal>catId</literal> avait déjà
+            été chargé par <literal>secondSession</literal> lorsque l'application a essayé de le
+            réattacher, une exception aurait été levée.
+        </para>
+
+        <para>
+            Utilisez <literal>update()</literal> si vous êtes sure que la session ne contient pas
+            déjà une instance persistante avec le même identifiant, et <literal>merge()</literal>
+            si vous voulez fusionner vos modifications n'importe quand sans considérer l'état de
+            la session. En d'autres mots, <literal>update()</literal> est généralement la première méthode
+            que vous devriez appeler dans une session fraîche, pour s'assurer que le réattachement
+            de vos instances détachées est la première opération qui est exécutée.
+        </para>
+
+        <para>
+            L'application devrait individuellement <literal>update()</literal> (NdT : mettre à jour)
+            les instances détachées accessibles depuis l'instance détachée donnée si et
+            <emphasis>seulement</emphasis> si elle veut que leur état soit aussi mis à jour. Ceci
+            peut être automatisé bien sûr, en utilisant la <emphasis>persistance transitive</emphasis>,
+            voir <xref linkend="objectstate-transitive"/>.
+        </para>
+
+        <para>
+            La méthode <literal>lock()</literal> permet aussi à une application de réassocier un
+            objet avec une nouvelle session. Pourtant, l'instance détachée doit être non modifiée !
+        </para>
+
+        <programlisting><![CDATA[//réassocie :
+sess.lock(fritz, LockMode.NONE);
+//fait une vérification de version, puis réassocie :
+sess.lock(izi, LockMode.READ);
+//fait une vérification de version, en utilisant SELECT ... FOR UPDATE, puis réassocie :
+sess.lock(pk, LockMode.UPGRADE);]]></programlisting>
+
+        <para>
+            Notez que <literal>lock()</literal> peut être utilisé avec différents
+            <literal>LockMode</literal>s, voir la documentation de l'API documentation et le chapitre
+            sur la gestion des transactions pour plus d'informations. Le réattachement n'est pas le seul
+            cas d'utilisation pour <literal>lock()</literal>.
+        </para>
+
+        <para>
+            D'autres modèles pour de longues unités de travail sont traités dans <xref linkend="transactions-optimistic"/>.
+        </para>
+
+    </sect1>
+
+    <sect1 id="objectstate-saveorupdate">
+        <title>Détection automatique d'un état</title>
+
+        <para>
+            Les utilisateurs d'Hibernate ont demandé une méthode dont l'intention générale
+            serait soit de sauvegarder une instance éphémère en générant un nouvel identifiant,
+            soit mettre à jour/réattacher les instances détachées associées à l'identifiant courant.
+            La méthode <literal>saveOrUpdate()</literal> implémente cette fonctionnalité.
+        </para>
+
+        <programlisting><![CDATA[// dans la première session
+Cat cat = (Cat) firstSession.load(Cat.class, catID);
+
+// dans une partie plus haute de l'application
+Cat mate = new Cat();
+cat.setMate(mate);
+
+// plus tard, dans une nouvelle session
+secondSession.saveOrUpdate(cat);   // met à jour un état existant (cat a un identifiant non-null)
+secondSession.saveOrUpdate(mate);  // sauvegarde les nouvelles instances (mate a un identiant null)]]></programlisting>
+
+        <para>
+            L'usage et la sémantique de <literal>saveOrUpdate()</literal> semble être confuse pour les
+            nouveaux utilisateurs. Premièrement, aussi longtemps que vous n'essayez pas d'utiliser des
+            instances d'une session dans une autre, vous ne devriez pas avoir besoin d'utiliser <literal>update()</literal>,
+            <literal>saveOrUpdate()</literal>, ou <literal>merge()</literal>. Certaines applications
+            n'utiliseront jamais ces méthodes.
+        </para>
+
+        <para>
+            Généralement <literal>update()</literal> ou <literal>saveOrUpdate()</literal> sont utilisées dans
+            le scénario suivant :
+        </para>
+
+        <itemizedlist spacing="compact">
+            <listitem>
+                <para>
+                    l'application charge un objet dans la première session
+                </para>
+            </listitem>
+            <listitem>
+                <para>
+                    l'objet est passé à la couche utilisateur
+                </para>
+            </listitem>
+            <listitem>
+                <para>
+                    certaines modifications sont effectuées sur l'objet
+                </para>
+            </listitem>
+            <listitem>
+                <para>
+                    l'objet est retourné à la couche logique métier
+                </para>
+            </listitem>
+            <listitem>
+                <para>
+                    l'application persiste ces modifications en appelant
+                    <literal>update()</literal> dans une seconde sessin
+                </para>
+            </listitem>
+        </itemizedlist>
+
+        <para>
+            <literal>saveOrUpdate()</literal> s'utilise dans le cas suivant :
+        </para>
+
+        <itemizedlist spacing="compact">
+            <listitem>
+                <para>
+                    si l'objet est déjà persistant dans cette session, ne rien faire
+                </para>
+            </listitem>
+            <listitem>
+                <para>
+                    si un autre objet associé à la session a le même identifiant, lever une exception
+                </para>
+            </listitem>
+            <listitem>
+                <para>
+                    si l'objet n'a pas de propriété d'identifiant, appeler <literal>save()</literal>
+                </para>
+            </listitem>
+            <listitem>
+                <para>
+                    si l'identifiant de l'objet a une valeur assignée à un objet nouvellement instancié,
+                    appeler <literal>save()</literal>
+                </para>
+            </listitem>
+            <listitem>
+                <para>
+                    si l'objet est versionné (par <literal>&lt;version&gt;</literal> ou
+                    <literal>&lt;timestamp&gt;</literal>), et la valeur de la propriété de version
+                    est la même valeur que celle assignée à un objet nouvellement instancié, appeler
+                    <literal>save()</literal>
+                </para>
+            </listitem>
+            <listitem>
+                <para>
+                    sinon mettre à jour l'objet avec <literal>update()</literal>
+                </para>
+            </listitem>
+        </itemizedlist>
+
+        <para>
+            et <literal>merge()</literal> est très différent :
+        </para>
+
+        <itemizedlist spacing="compact">
+            <listitem>
+                <para>
+                    s'il y a une instance persistante avec le même identifiant couramment
+                    associée à la session, copier l'état de l'objet donné dans l'instance persistante
+                </para>
+            </listitem>
+            <listitem>
+                <para>
+                    s'il n'y a pas d'instance persistante associée à cette session, essayer de le charger
+                    à partir de la base de données, ou créer une nouvelle instance persistante
+                </para>
+            </listitem>
+            <listitem>
+                <para>
+                    l'instance persistante est retournée
+                </para>
+            </listitem>
+            <listitem>
+                <para>
+                    l'instance donnée ne devient pas associée à la session, elle reste détachée
+                </para>
+            </listitem>
+        </itemizedlist>
+
+    </sect1>
+
+    <sect1 id="objectstate-deleting" revision="1">
+        <title>Suppression d'objets persistants</title>
+
+        <para>
+            <literal>Session.delete()</literal> supprimera l'état d'un objet de la base de données.
+            Bien sûr, votre application pourrait encore conserver une référence vers un objet effacé.
+            Il est mieux de penser à <literal>delete()</literal> comme rendant une instance persistante
+            éphémère.
+        </para>
+
+        <programlisting><![CDATA[sess.delete(cat);]]></programlisting>
+
+        <para>
+            Vous pouvez effacer des objets dans l'ordre que vous voulez, sans risque de violations
+            de contrainte de clef étrangère. Il est encore possible de violer une contrainte <literal>NOT
+            NULL</literal> sur une colonne de clef étrangère en effaçant des objets dans le
+            mauvais ordre, par exemple si vous effacer le parent, mais oubliez d'effacer les enfants.
+        </para>
+
+    </sect1>
+
+    <sect1 id="objectstate-replicating" revision="1">
+        <title>Réplication d'objets entre deux entrepôts de données</title>
+
+        <para>
+            Il est occasionnellement utile de pouvoir prendre un graphe d'instances persistantes
+            et de les rendre persistantes dans un entrepôt différent, sans regénérer les valeurs
+            des identifiants.
+        </para>
+
+        <programlisting><![CDATA[//récupère un cat de la base de données
+Session session1 = factory1.openSession();
+Transaction tx1 = session1.beginTransaction();
+Cat cat = session1.get(Cat.class, catId);
+tx1.commit();
+session1.close();
+
+// réconcilie la seconde base de données
+Session session2 = factory2.openSession();
+Transaction tx2 = session2.beginTransaction();
+session2.replicate(cat, ReplicationMode.LATEST_VERSION);
+tx2.commit();
+session2.close();]]></programlisting>
+
+        <para>
+            Le <literal>ReplicationMode</literal> détermine comment <literal>replicate()</literal>
+            traitera les conflits avec les lignes existantes dans la base de données.
+        </para>
+
+        <itemizedlist spacing="compact">
+            <listitem>
+                <para>
+                    <literal>ReplicationMode.IGNORE</literal> - ignore l'objet s'il y a une ligne
+                    existante dans la base de données avec le même identifiant
+                </para>
+            </listitem>
+            <listitem>
+                <para>
+                    <literal>ReplicationMode.OVERWRITE</literal> - écrase n'importe quelle ligne existante
+                    dans la base de données avec le même identifiant
+                </para>
+            </listitem>
+            <listitem>
+                <para>
+                    <literal>ReplicationMode.EXCEPTION</literal> - lève une exception s'il y une ligne dans
+                    la base de données avec le même identifiant
+                </para>
+            </listitem>
+            <listitem>
+                <para>
+                    <literal>ReplicationMode.LATEST_VERSION</literal> - écrase la ligne si son numéro de version
+                    est plus petit que le numéro de version de l'objet, ou ignore l'objet sinon
+                </para>
+            </listitem>
+        </itemizedlist>
+
+        <para>
+            Les cas d'utilisation de cette fonctionnalité incluent la réconciliation de données
+            entrées dans différentes base de données, l'extension des informations de configuration
+            du système durant une mise à jour du produit, retour en arrière sur les changements effectués
+            durant des transactions non-ACID, et plus.
+        </para>
+
+    </sect1>
+
+    <sect1 id="objectstate-flushing">
+        <title>Flush de la session</title>
+
+        <para>
+            De temps en temps la <literal>Session</literal> exécutera les expressions SQL
+            requises pour syncrhoniser l'état de la connexion JDBC avec l'état des objets
+            retenus en mémoire. Ce processus, <emphasis>flush</emphasis>, arrive par défaut aux
+            points suivants :
+        </para>
+
+        <itemizedlist spacing="compact">
+            <listitem>
+                <para>
+                    lors de certaines exécutions de requête
+                </para>
+            </listitem>
+            <listitem>
+                <para>
+                    lors d'un appel à <literal>org.hibernate.Transaction.commit()</literal>
+                </para>
+            </listitem>
+            <listitem>
+                <para>
+                    lors d'un appel à <literal>Session.flush()</literal>
+                </para>
+            </listitem>
+        </itemizedlist>
+
+        <para>
+            Les expressions SQL sont effectuées dans l'ordre suivant :
+        </para>
+
+        <orderedlist spacing="compact">
+            <listitem>
+                <para>
+                    insertion des entités, dans le même ordre que celui des
+                    objets correspondants sauvegardés par l'appel à <literal>Session.save()</literal>
+                </para>
+            </listitem>
+            <listitem>
+                <para>
+                    mise à jours des entités
+                </para>
+            </listitem>
+            <listitem>
+                <para>
+                    suppression des collections
+                </para>
+            </listitem>
+            <listitem>
+                <para>
+                    suppression, mise à jour et insertion des éléments des collections
+                </para>
+            </listitem>
+            <listitem>
+                <para>
+                    insertion des collections
+                </para>
+            </listitem>
+            <listitem>
+                <para>
+                    suppression des entités, dans le même ordre que celui des objets
+                    correspondants qui ont été supprimés par l'appel à <literal>Session.delete()</literal>
+                </para>
+            </listitem>
+        </orderedlist>
+
+        <para>
+            (Une exception est que des objets utilisant la génération <literal>native</literal>
+            d'identifiants sont insérés lorsqu'ils sont sauvegardés.)
+        </para>
+
+        <para>
+            Excepté lorsque vous appelez <literal>flush()</literal> explicitement, il n'y
+            absolument aucune garantie à propos de <emphasis>quand</emphasis> la <literal>Session</literal>
+            exécute les appels JDBC, seulement sur l'<emphasis>ordre</emphasis> dans lequel ils sont
+            exécutés. Cependant, Hibernate garantit que <literal>Query.list(..)</literal> ne
+            retournera jamais de données périmées, ni des données fausses.
+        </para>
+
+        <para>
+            Il est possible de changer le comportement par défaut, donc que le flush se produise
+            moins fréquemment. La classe <literal>FlushMode</literal> définit trois modes différents :
+            flush seulement lors du commit (et seulement quand l'API <literal>Transaction</literal>
+            d'Hibernate est utilisée), flush automatiquement en utilisant la procédure expliquée, ou
+            jamais de flush à moins que <literal>flush()</literal> soit appelée explicitement.
+            Le dernier mode est utile pour l'exécution de longues unités de travail, où une
+            <literal>Session</literal> est gardée ouverte et déconnectée pour un long moment
+            (voir <xref linkend="transactions-optimistic-longsession"/>).
+        </para>
+
+        <programlisting><![CDATA[sess = sf.openSession();
+Transaction tx = sess.beginTransaction();
+sess.setFlushMode(FlushMode.COMMIT); // permet aux requêtes de retourner un état périmé
+
+Cat izi = (Cat) sess.load(Cat.class, id);
+izi.setName(iznizi);
+
+// pourrait retourner des données périmées
+sess.find("from Cat as cat left outer join cat.kittens kitten");
+
+// le changement pour izi n'est pas flushé !
+...
+tx.commit(); // le flush se produit]]></programlisting>
+
+        <para>
+            Durant le flush, une exception peut se produire (par exemple, si une opération de la
+            DML viole une contrainte). Puisque les exceptions de gestion impliquent une certaine
+            compréhension du comportement transactionnel d'Hibernate, nous le traitons dans
+            <xref linkend="transactions"/>.
+        </para>
+
+    </sect1>
+
+    <sect1 id="objectstate-transitive" revision="1">
+        <title>Persistance transitive</title>
+
+        <para>
+            Il est assez pénible de sauvegarder, supprimer, ou réattacher des objets
+            un par un, surtout si vous traitez un graphe d'objets associés. Un cas habituel
+            est une relation parent/enfant. Considérez l'exemple suivant :
+        </para>
+
+        <para>
+            Si les enfants de la relation parent/enfant étaient des types de valeur (par exemple,
+            une collection d'adresses ou de chaînes de caractères), leur cycle de vie dépendraient
+            du parent et aucune action ne serait requise pour "cascader" facilement les
+            changements d'état. Si le parent est sauvegardé, les objets enfants de type de valeur sont
+            sauvegardés également, si le parent est supprimé, les enfants sont supprimés, etc. Ceci
+            fonctionne même pour des opérations telles que la suppression d'un enfant de la collection ;
+            Hibernate détectera cela et, puisque les objets de type de valeur ne peuvent pas avoir
+            des références partagées, supprimera l'enfant de la base de données.
+        </para>
+
+        <para>
+            Maintenant considérez le même scénario avec un parent et dont les objets enfants
+            sont des entités, et non des types de valeur (par exemple, des catégories et des
+            objets, ou un parent et des chatons). Les entités ont leur propre cycle de vie,
+            supportent les références partagées (donc supprimer une entité de la collection
+            ne signifie pas qu'elle peut être supprimée), et il n'y a par défaut pas de
+            cascade d'état d'une entité vers n'importe quelle entité associée. Hibernate
+            n'implémente pas la <emphasis>persistance par accessibilité</emphasis> par défaut.
+        </para>
+
+        <para>
+            Pour chaque opération basique de la session d'Hibernate - incluant <literal>persist(), merge(),
+            saveOrUpdate(), delete(), lock(), refresh(), evict(), replicate()</literal> - il y a un
+            style de cascade correspondant. Respectivement, les styles de cascade s'appellent <literal>persist,
+            merge, save-update, delete, lock, refresh, evict, replicate</literal>. Si vous voulez qu'une
+            opération soit cascadée le long d'une association, vous devez l'indiquer dans le document de
+            mapping. Par exemple :
+        </para>
+
+        <programlisting><![CDATA[<one-to-one name="person" cascade="persist"/>]]></programlisting>
+
+        <para>
+            Les styles de cascade peuvent être combinés :
+        </para>
+
+        <programlisting><![CDATA[<one-to-one name="person" cascade="persist,delete,lock"/>]]></programlisting>
+
+        <para>
+            Vous pouvez même utiliser <literal>cascade="all"</literal> pour spécifier que <emphasis>toutes</emphasis>
+            les opérations devraient être cascadées le long de l'association. La valeur par défaut
+            <literal>cascade="none"</literal> spécifie qu'aucune opération ne sera cascadée.
+        </para>
+
+        <para>
+            Une style de cascade spécial, <literal>delete-orphan</literal>, s'applique seulement
+            aux associations un-vers-plusieurs, et indique que l'opération <literal>delete()</literal>
+            devrait être appliquée à n'importe quel enfant qui est supprimé de l'association.
+        </para>
+
+
+        <para>
+            Recommandations :
+        </para>
+
+       <itemizedlist spacing="compact">
+            <listitem>
+                <para>
+                    Cela n'a généralement aucun sens d'activer la cascade sur une association
+                    <literal>&lt;many-to-one&gt;</literal> ou <literal>&lt;many-to-many&gt;</literal>. Les
+                    cascades sont souvent utiles pour des associations
+                    <literal>&lt;one-to-one&gt;</literal> et <literal>&lt;one-to-many&gt;</literal>.
+                </para>
+            </listitem>
+            <listitem>
+                <para>
+                    Si la durée de vie de l'objet enfant est liée à la durée de vie de l'objet parent,
+                    faites en un <emphasis>objet du cycle de vie</emphasis> en spécifiant
+                    <literal>cascade="all,delete-orphan"</literal>.
+                </para>
+            </listitem>
+            <listitem>
+                <para>
+                    Sinon, vous pourriez ne pas avoir besoin de cascade du tout. Mais si vous pensez que vous
+                    travaillerez souvent avec le parent et les enfants ensemble dans la même transaction, et
+                    que vous voulez vous éviter quelques frappes, considérez l'utilisation de
+                    <literal>cascade="persist,merge,save-update"</literal>.
+                </para>
+            </listitem>
+        </itemizedlist>
+
+        <para>
+            Mapper une association (soit une simple association valuée, soit une collection) avec
+            <literal>cascade="all"</literal> marque l'association comme une relation de style
+            <emphasis>parent/enfant</emphasis> où la sauvegarde/mise à jour/suppression du parent
+            entraîne la sauvegarde/mise à jour/suppression de l'enfant ou des enfants.
+        </para>
+        <para>
+            En outre, une simple référence à un enfant d'un parent persistant aura pour conséquence
+            la sauvegarde/mise à jour de l'enfant. Cette métaphore est cependant incomplète. Un enfant
+            qui devient non référencé par son parent <emphasis>n'est pas</emphasis> automatiquement
+            supprimée, excepté dans le cas d'une association <literal>&lt;one-to-many&gt;</literal>
+            mappée avec <literal>cascade="delete-orphan"</literal>. La sémantique précise des opérations
+            de cascade pour une relation parent/enfant est la suivante :
+        </para>
+
+       <itemizedlist spacing="compact">
+            <listitem>
+                <para>
+                    Si un parent est passé à <literal>persist()</literal>, tous les enfant sont passés à
+                    <literal>persist()</literal>
+                </para>
+            </listitem>
+            <listitem>
+                <para>
+                    Si un parent est passé à <literal>merge()</literal>, tous les enfants sont passés à
+                    <literal>merge()</literal>
+                </para>
+            </listitem>
+            <listitem>
+                <para>
+                    Si un parent est passé à <literal>save()</literal>, <literal>update()</literal> ou
+                    <literal>saveOrUpdate()</literal>, tous les enfants sont passés à <literal>saveOrUpdate()</literal>
+                </para>
+            </listitem>
+            <listitem>
+                <para>
+                    Si un enfant détaché ou éphémère devient référencé par un parent persistant,
+                    il est passé à <literal>saveOrUpdate()</literal>
+                </para>
+            </listitem>
+            <listitem>
+                <para>
+                    Si un parent est supprimé, tous les enfants sont passés à <literal>delete()</literal>
+                </para>
+            </listitem>
+            <listitem>
+                <para>
+                    Si un enfant est déréférencé par un parent persistant, <emphasis>rien de spécial
+                    n'arrive</emphasis> - l'application devrait explicitement supprimer l'enfant si nécessaire -
+                    à moins que <literal>cascade="delete-orphan"</literal> soit paramétré,
+                    au quel cas l'enfant "orphelin" est supprimé.
+                </para>
+            </listitem>
+        </itemizedlist>
+		
+		<para>
+            Enfin, la cascade des opérations peut être effectuée sur un graphe donné lors
+			de l'<emphasis>appel de l'opération</emphasis> or lors du <emphasis>flush</emphasis>
+			suivant. Toutes les opérations, lorsque cascadées, le sont sur toutes les entités
+			associées atteignables lorsque l'opétation est exécutée. Cependant 
+			<literal>save-upate</literal> et <literal>delete-orphan</literal> sont cascadées
+            à toutes les entités associées atteignables lors du flush de la 
+            <literal>Session</literal>.
+        </para>
+
+    </sect1>
+
+    <sect1 id="objectstate-metadata">
+        <title>Utilisation des méta-données</title>
+
+        <para>
+            Hibernate requiert un modèle de méta-niveau très riche de toutes les entités et types valués.
+            De temps en temps, ce modèle est très utile à l'application elle même. Par exemple,
+            l'application pourrait utiliser les méta-données d'Hibernate pour implémenter un algorithme
+            de copie en profondeur "intelligent" qui comprendrait quels objets devraient copiés
+            (par exemple les types de valeur mutables) et lesquels ne devraient pas l'être (par exemple
+            les types de valeurs immutables et, possiblement, les entités associées).
+        </para>
+        <para>
+            Hibernate expose les méta-données via les interfaces <literal>ClassMetadata</literal>
+            et <literal>CollectionMetadata</literal> et la hiérarchie <literal>Type</literal>.
+            Les instances des interfaces de méta-données peuvent être obtenues à partir de la
+            <literal>SessionFactory</literal>.
+        </para>
+
+        <programlisting><![CDATA[Cat fritz = ......;
+ClassMetadata catMeta = sessionfactory.getClassMetadata(Cat.class);
+
+Object[] propertyValues = catMeta.getPropertyValues(fritz);
+String[] propertyNames = catMeta.getPropertyNames();
+Type[] propertyTypes = catMeta.getPropertyTypes();
+
+// récupère une Map de toutes les propriétés qui ne sont pas des collections ou des associations
+Map namedValues = new HashMap();
+for ( int i=0; i<propertyNames.length; i++ ) {
+    if ( !propertyTypes[i].isEntityType() && !propertyTypes[i].isCollectionType() ) {
+        namedValues.put( propertyNames[i], propertyValues[i] );
+    }
+}]]></programlisting>
+
+    </sect1>
+
+</chapter>

Copied: core/trunk/documentation/manual/fr-FR/src/main/docbook/content/toolset_guide.xml (from rev 14070, core/trunk/documentation/manual/fr-FR/src/main/docbook/modules/toolset_guide.xml)
===================================================================
--- core/trunk/documentation/manual/fr-FR/src/main/docbook/content/toolset_guide.xml	                        (rev 0)
+++ core/trunk/documentation/manual/fr-FR/src/main/docbook/content/toolset_guide.xml	2007-10-09 18:28:36 UTC (rev 14074)
@@ -0,0 +1,594 @@
+<?xml version="1.0" encoding="iso-8859-1"?>
+<chapter id="toolsetguide" revision="2">
+    <title>Guide des outils</title>
+
+    <para>
+        Des outils en ligne de commande, des plugins Eclipse ainsu que des tâches Ant permettent de gérer de cycles de développement complet
+    de projets utilisant Hibernate.
+    </para>
+
+    <para>
+        Les <emphasis>outils Hibernate</emphasis> actuels incluent des plugins pour l'IDE Eclipse ainsi que des tâches Ant pour l'ingénierie 
+        inverse de bases de données existantes :
+    </para>
+
+    <itemizedlist>
+        <listitem><para>
+            <emphasis>Mapping Editor :</emphasis> un éditeur pour les fichiers de mapping XML Hibernate, supportant l'auto-complétion et la mise en valeur de la syntaxe.
+            Il supporte aussi l'auto-complétion automatique pour les noms de classes et les noms de propriété/champ,
+            le rendant beaucoup plus polyvalent qu'un éditeurXML normal.
+        </para></listitem>
+        <listitem><para>
+            <emphasis>Console :</emphasis> la console est une nouvelle vue d'Eclipse. En plus de la vue d'ensemble
+            arborescente de vos configurations de console, vous obtenez aussi une vue interactive de vos classes persistantes et de leurs relations.
+            La console vous permet d'exécuter des requête HQL dans votre base de données et de parcourir les résultats directement dans Eclipse.
+        </para></listitem>
+        <listitem><para>
+            <emphasis>Development Wizards :</emphasis> plusieurs assistants sont fournis avec les outils d'Hibernate
+            pour Eclipse ; vous pouvez utiliser un assistant pour générer rapidement les fichiers de configuration d'Hibernate (cfg.xml),
+            ou vous pouvez même complètement générer les fichiers de mapping Hibernate et les sources des POJOs à partir d'un schéma de base de données existant.
+            L'assistant d'ingénierie inverse supporte les modèles utilisateur.
+        </para></listitem>
+        <listitem><para>
+            <emphasis>Tâches Ant :</emphasis>
+        </para></listitem>
+
+    </itemizedlist>
+
+    <para>
+        Veuillez-vous référer au paquet <emphasis>outils Hibernate</emphasis> et sa documentation pour plus d'informations.
+    </para>
+
+    <para>
+        Pourtant, le paquet principal d'Hibernate arrive avec un lot d'outils intégrés (il peut même être utilisé de "l'intérieur" d'Hibernate à la volée) :
+        <emphasis>SchemaExport</emphasis> aussi connu comme
+        <literal>hbm2ddl</literal>.
+    </para>
+
+    <sect1 id="toolsetguide-s1" revision="2">
+        <title>Génération automatique du schéma</title>
+
+        <para>
+            La DDL peut être générée à partir de vos fichiers de mapping par un utilitaire d'Hibernate. Le schéma généré
+            inclut les contraintes d'intégrité référentielle (clefs primaires et étrangères) pour les tables d'entités
+            et de collections. Les tables et les séquences sont aussi créées pour les générateurs d'identifiant mappés.
+        </para>
+
+        <para>
+            Vous <emphasis>devez</emphasis> spécifier un <literal>Dialect</literal> SQL via la propriété
+            <literal>hibernate.dialect</literal> lors de l'utilisation de cet outils, puisque la DDL est
+            fortement dépendante de la base de données.
+        </para>
+
+        <para>
+            D'abord, personnalisez vos fichiers de mapping pour améliorer le schéma généré.
+        </para>
+
+        <sect2 id="toolsetguide-s1-2" revision="3">
+            <title>Personnaliser le schéma</title>
+
+            <para>
+                Plusieurs éléments du mapping hibernate définissent des attributs optionnels
+                nommés <literal>length</literal>, <literal>precision</literal> et <literal>scale</literal>.
+                Vous pouvez paramétrer la longueur, la précision,...  d'une colonne avec ces attributs.
+            </para>
+            
+            <programlisting><![CDATA[<property name="zip" length="5"/>]]></programlisting>
+            <programlisting><![CDATA[<property name="balance" precision="12" scale="2"/>]]></programlisting>
+
+            <para>
+                Certains éléments acceptent aussi un attribut <literal>not-null</literal>
+                (utilisé pour générer les contraintes de colonnes <literal>NOT NULL</literal>) et
+                un attribut <literal>unique</literal> (pour générer une contrainte de colonne
+                <literal>UNIQUE</literal>).
+            </para>
+            
+            <programlisting><![CDATA[<many-to-one name="bar" column="barId" not-null="true"/>]]></programlisting>
+            <programlisting><![CDATA[<element column="serialNumber" type="long" not-null="true" unique="true"/>]]></programlisting>
+
+            <para>
+                Un attribut <literal>unique-key</literal> peut être utilisé pour grouper les colonnes
+                en une seule contrainte d'unicité. Actuellement, la valeur spécifiée par
+                l'attribut <literal>unique-key</literal> n'est <emphasis>pas</emphasis> utilisée pour
+                nommer la contrainte dans le DDL généré, elle sert juste à grouper les colonnes
+                dans le fichier de mapping.
+            </para>
+            <programlisting><![CDATA[<many-to-one name="org" column="orgId" unique-key="OrgEmployeeId"/>
+            <property name="employeeId" unique-key="OrgEmployeeId"/>]]></programlisting>
+
+            <para>
+                Un attribut <literal>index</literal> indique le nom d'un index qui sera
+                créé  en utilisant la ou les colonnes mappées. Plusieurs colonnes
+                peuvent être groupées dans un même index, en spécifiant le même
+                nom d'index. 
+            </para>
+
+            <programlisting><![CDATA[<property name="lastName" index="CustName"/>
+<property name="firstName" index="CustName"/>]]></programlisting>
+
+            <para>
+                Un attribut <literal>foreign-key</literal> peut être utilisé pour surcharger le nom
+                des clés étrangères générées.
+            </para>
+            
+            <programlisting><![CDATA[<many-to-one name="bar" column="barId" foreign-key="FKFooBar"/>]]></programlisting>
+
+            <para>
+                Plusieurs éléments de mapping acceptent aussi un élément fils <literal>&lt;column&gt;</literal>. 
+                Ceci est utile pour les type multi-colonnes:
+            </para>
+
+            <programlisting><![CDATA[<property name="name" type="my.customtypes.Name"/>
+    <column name="last" not-null="true" index="bar_idx" length="30"/>
+    <column name="first" not-null="true" index="bar_idx" length="20"/>
+    <column name="initial"/>
+</property>]]></programlisting>
+
+            <para>
+                L'attribut <literal>default</literal> vous laisse spécifier une valeur par défaut pour
+                une colonnes (vous devriez assigner la même valeur à la propriété mappée avant de sauvegarder une nouvelle instance
+                de la classe mappée).
+            </para>
+
+            <programlisting><![CDATA[<property name="credits" type="integer" insert="false">
+    <column name="credits" default="10"/>
+</property>]]></programlisting>
+
+            <programlisting><![CDATA[<version name="version" type="integer" insert="false">
+    <column name="version" default="0"/>
+</property>]]></programlisting>
+
+            <para>
+                L'attribut <literal>sql-type</literal> laisse l'utilisateur surcharger le mapping
+                par défaut du type Hibernate vers un type SQL.
+            </para>
+            
+            <programlisting><![CDATA[<property name="balance" type="float">
+    <column name="balance" sql-type="decimal(13,3)"/>
+</property>]]></programlisting>
+            
+
+            <para>
+                L'attribut <literal>check</literal> permet de spécifier une contrainte de vérification.
+            </para>
+
+            <programlisting><![CDATA[<property name="foo" type="integer">
+    <column name="foo" check="foo > 10"/>
+</property>]]></programlisting>
+
+            <programlisting><![CDATA[<class name="Foo" table="foos" check="bar < 100.0">
+    ...
+    <property name="bar" type="float"/>
+</class>]]></programlisting>
+
+
+            <table frame="topbot" id="schemattributes-summary" revision="2">
+                <title>Summary</title>
+                <tgroup cols="3">
+                    <colspec colwidth="1*"/>
+                    <colspec colwidth="1*"/>
+                    <colspec colwidth="2.5*"/>
+                    <thead>
+                        <row>
+                            <entry>Attribut</entry>
+                            <entry>Valeur</entry>
+                            <entry>Interprétation</entry>
+                        </row>
+                    </thead>
+                    <tbody>
+                        <row>
+                            <entry><literal>length</literal></entry>
+                            <entry>numérique</entry>
+                            <entry>taille d'une colonne</entry>
+                        </row>
+                        <row>
+                            <entry><literal>precision</literal></entry>
+                            <entry>numérique</entry>
+                            <entry>précision décimale de la colonne</entry>
+                        </row>
+                        <row>
+                            <entry><literal>scale</literal></entry>
+                            <entry>numérique</entry>
+                            <entry>scale décimale de la colonne</entry>
+                        </row>
+                        <row>
+                            <entry><literal>not-null</literal></entry>
+                            <entry><literal>true|false</literal></entry>
+                            <entry>spécifie que la colonne doit être non-nulle</entry>
+                        </row>
+                        <row>
+                            <entry><literal>unique</literal></entry>
+                            <entry><literal>true|false</literal></entry>
+                            <entry>spécifie que la colonne doit avoir une contrainte d'unicité</entry>
+                        </row>
+                        <row>
+                            <entry><literal>index</literal></entry>
+                            <entry><literal>index_name</literal></entry>
+                            <entry>spécifie le nom d'un index (multi-colonnes)</entry>
+                        </row>
+                        <row>
+                            <entry><literal>unique-key</literal></entry>
+                            <entry><literal>unique_key_name</literal></entry>
+                            <entry>spécifie le nom d'une contrainte d'unicité multi-colonnes</entry>
+                        </row>
+                        <row>
+                            <entry><literal>foreign-key</literal></entry>
+                            <entry><literal>foreign_key_name</literal></entry>
+                            <entry>
+                                spécifie le nom d'une contrainte de clé étrangère générée pour
+                                une association, utilisez-la avec les éléments de mapping
+                                &lt;one-to-one&gt;, &lt;many-to-one&gt;, &lt;key&gt;, et &lt;many-to-many&gt;
+                                Notez que les extrêmités <literal>inverse="true"</literal>
+                                se seront pas prises en compte par <literal>SchemaExport</literal>.
+                            </entry>
+                        </row>
+                        <row>
+                            <entry><literal>sql-type</literal></entry>
+                            <entry><literal>SQL column_type</literal></entry>
+                            <entry>
+                                surcharge le type par défaut (attribut de
+                                l'élément <literal>&lt;column&gt;</literal> uniquement)
+                            </entry>
+                       </row>
+                       <row>
+                            <entry><literal>default</literal></entry>
+                            <entry>expression SQL</entry>
+                            <entry>
+                                spécifie une valeur par défaut pour la colonne
+                            </entry>
+                       </row>
+                       <row>
+                            <entry><literal>check</literal></entry>
+                            <entry>SQL expression</entry>
+                            <entry>
+                                crée une contrainte de vérification sur la table ou la colonne
+                            </entry>
+                       </row>
+                   </tbody>
+                </tgroup>
+            </table>
+
+            <para>
+                L'élément <literal>&lt;comment&gt;</literal> vous permet de spécifier un commentaire pour le schéma généré.
+            </para>
+
+            <programlisting><![CDATA[<class name="Customer" table="CurCust">
+    <comment>Current customers only</comment>
+    ...
+</class>]]></programlisting>
+
+            <programlisting><![CDATA[<property name="balance">
+    <column name="bal">
+        <comment>Balance in USD</comment>
+    </column>
+</property>]]></programlisting>
+
+            <para>
+                Ceci a pour résultat une expression
+                <literal>comment on table</literal> ou
+                <literal>comment on column</literal> dans la DDL générée (où supportée).
+            </para>
+
+        </sect2>
+
+        <sect2 id="toolsetguide-s1-3" revision="2">
+            <title>Exécuter l'outil</title>
+
+            <para>
+                L'outil <literal>SchemaExport</literal> génère un script DDL vers
+                la sortie standard et/ou exécute les ordres DDL.
+            </para>
+
+            <para>
+                <literal>java -cp </literal><emphasis>classpath_hibernate</emphasis>
+                <literal>net.sf.hibernate.tool.hbm2ddl.SchemaExport</literal> <emphasis>options fichiers_de_mapping</emphasis>
+            </para>
+
+            <table frame="topbot">
+                <title><literal>SchemaExport</literal> Options de la ligne de commande</title>
+                <tgroup cols="2">
+                    <colspec colwidth="1.5*"/>
+                    <colspec colwidth="2*"/>
+                    <thead>
+                        <row>
+                            <entry>Option</entry>
+                            <entry>Description</entry>
+                        </row>
+                    </thead>
+                    <tbody>
+                        <row>
+                            <entry><literal>--quiet</literal></entry>
+                            <entry>ne pas écrire le script vers la sortie standard</entry>
+                        </row>
+                        <row>
+                            <entry><literal>--drop</literal></entry>
+                            <entry>supprime seuleument les tables</entry>
+                        </row>
+                        <row>
+                            <entry><literal>--create</literal></entry>
+                            <entry>ne créé que les tables</entry>
+                        </row>
+                        <row>
+                            <entry><literal>--text</literal></entry>
+                            <entry>ne pas exécuter sur la base de données</entry>
+                        </row>
+                        <row>
+                            <entry><literal>--output=my_schema.ddl</literal></entry>
+                            <entry>écrit le script ddl vers un fichier</entry>
+                        </row>
+                        <row>
+                            <entry><literal>--naming=eg.MyNamingStrategy</literal></entry>
+                            <entry>sélectionne une <literal>NamingStrategy</literal></entry>
+                        </row>
+                        <row>
+                            <entry><literal>--config=hibernate.cfg.xml</literal></entry>
+                            <entry>lit la configuration Hibernate à partir d'un fichier XML</entry>
+                        </row>
+                        <row>
+                            <entry><literal>--properties=hibernate.properties</literal></entry>
+                            <entry>lit les propriétés de la base de données à partir d'un fichier</entry>
+                        </row>
+                        <row>
+                            <entry><literal>--format</literal></entry>
+                            <entry>formatte proprement le SQL généré dans le script</entry>
+                        </row>
+                        <row>
+                            <entry><literal>--delimiter=x</literal></entry>
+                            <entry>paramètre un délimiteur de fin de ligne pour le script</entry>
+                        </row>
+                    </tbody>
+                </tgroup>
+            </table>
+
+            <para>
+                Vous pouvez même intégrer <literal>SchemaExport</literal> dans votre application :
+            </para>
+
+            <programlisting><![CDATA[Configuration cfg = ....;
+new SchemaExport(cfg).create(false, true);]]></programlisting>
+
+        </sect2>
+
+        <sect2 id="toolsetguide-s1-4">
+            <title>Propriétés</title>
+
+            <para>
+                Les propriétés de la base de données peuvent être spécifiées
+            </para>
+
+            <itemizedlist spacing="compact">
+                <listitem>
+                    <para>comme propriétés système avec <literal>-D</literal><emphasis>&lt;property&gt;</emphasis></para>
+                </listitem>
+                <listitem>
+                    <para>dans <literal>hibernate.properties</literal></para>
+                </listitem>
+                <listitem>
+                    <para>dans un fichier de propriétés déclaré avec <literal>--properties</literal></para>
+                </listitem>
+            </itemizedlist>
+
+            <para>
+                Les propriétés nécessaires sont :
+            </para>
+
+            <table frame="topbot">
+                <title>SchemaExport Connection Properties</title>
+                <tgroup cols="2">
+                    <colspec colwidth="1.5*"/>
+                    <colspec colwidth="2*"/>
+                    <thead>
+                        <row>
+                            <entry>Nom de la propriété</entry>
+                            <entry>Description</entry>
+                        </row>
+                    </thead>
+                    <tbody>
+                    <row>
+                        <entry><literal>hibernate.connection.driver_class</literal></entry>
+                        <entry>classe du driver JDBC</entry>
+                    </row>
+                    <row>
+                        <entry><literal>hibernate.connection.url</literal></entry>
+                        <entry>URL JDBC</entry>
+                    </row>
+                    <row>
+                        <entry><literal>hibernate.connection.username</literal></entry>
+                        <entry>utilisateur de la base de données</entry>
+                    </row>
+                    <row>
+                        <entry><literal>hibernate.connection.password</literal></entry>
+                        <entry>mot de passe de l'utilisateur</entry>
+                    </row>
+                    <row>
+                        <entry><literal>hibernate.dialect</literal></entry>
+                        <entry>dialecte</entry>
+                    </row>
+                    </tbody>
+                </tgroup>
+            </table>
+
+        </sect2>
+
+        <sect2 id="toolsetguide-s1-5">
+            <title>Utiliser Ant</title>
+
+            <para>
+                Vous pouvez appeler <literal>SchemaExport</literal> depuis votre script
+                de construction Ant :
+            </para>
+
+            <programlisting><![CDATA[<target name="schemaexport">
+    <taskdef name="schemaexport"
+        classname="org.hibernate.tool.hbm2ddl.SchemaExportTask"
+        classpathref="class.path"/>
+
+    <schemaexport
+        properties="hibernate.properties"
+        quiet="no"
+        text="no"
+        drop="no"
+        delimiter=";"
+        output="schema-export.sql">
+        <fileset dir="src">
+            <include name="**/*.hbm.xml"/>
+        </fileset>
+    </schemaexport>
+</target>]]></programlisting>
+
+        </sect2>
+
+        <sect2 id="toolsetguide-s1-6" revision="2">
+            <title>Mises à jour incrémentales du schéma</title>
+
+            <para>
+                L'outil <literal>SchemaUpdate</literal> mettra à jour un schéma existant
+                en effectuant les changement par "incrément".
+                Notez que <literal>SchemaUpdate</literal> dépends beaucoup de l'API JDBC
+                metadata, il ne fonctionnera donc pas avec tous les drivers JDBC.
+            </para>
+
+            <para>
+                <literal>java -cp </literal><emphasis>classpath_hibernate</emphasis>
+                <literal>net.sf.hibernate.tool.hbm2ddl.SchemaUpdate</literal> <emphasis>options fichiers_de_mapping</emphasis>
+            </para>
+
+            <table frame="topbot">
+                <title><literal>SchemaUpdate</literal> Options de ligne de commande</title>
+                <tgroup cols="2">
+                    <colspec colwidth="1.5*"/>
+                    <colspec colwidth="2*"/>
+                    <thead>
+                        <row>
+                            <entry>Option</entry>
+                            <entry>Description</entry>
+                        </row>
+                    </thead>
+                    <tbody>
+                        <row>
+                            <entry><literal>--quiet</literal></entry>
+                            <entry>ne pas écrire vers la sortie standard</entry>
+                        </row>
+                        <row>
+                            <entry><literal>--text</literal></entry>
+                            <entry>ne pas exporter vers la base de données</entry>
+                        </row>
+                        <row>
+                            <entry><literal>--naming=eg.MyNamingStrategy</literal></entry>
+                            <entry>choisit une <literal>NamingStrategy</literal></entry>
+                        </row>
+                        <row>
+                            <entry><literal>--properties=hibernate.properties</literal></entry>
+                            <entry>lire les propriétés de la base de données à partir d'un fichier</entry>
+                        </row>
+                     </tbody>
+                </tgroup>
+            </table>
+
+            <para>
+                Vous pouvez intégrer <literal>SchemaUpdate</literal> dans votre application :
+            </para>
+
+            <programlisting><![CDATA[Configuration cfg = ....;
+new SchemaUpdate(cfg).execute(false);]]></programlisting>
+
+        </sect2>
+
+        <sect2 id="toolsetguide-s1-7">
+            <title>Utiliser Ant pour des mises à jour de schéma par incrément</title>
+
+            <para>
+                Vous pouvez appeler <literal>SchemaUpdate</literal> depuis le script Ant :
+            </para>
+
+            <programlisting><![CDATA[<target name="schemaupdate">
+    <taskdef name="schemaupdate"
+        classname="org.hibernate.tool.hbm2ddl.SchemaUpdateTask"
+        classpathref="class.path"/>
+
+    <schemaupdate
+        properties="hibernate.properties"
+        quiet="no">
+        <fileset dir="src">
+            <include name="**/*.hbm.xml"/>
+        </fileset>
+    </schemaupdate>
+</target>]]></programlisting>
+
+        <sect2 id="toolsetguide-s1-8" revision="1">
+            <title>Validation du schéma</title>
+
+            <para>
+                L'outil <literal>SchemaValidator</literal> validera que le schéma existant correspond à vos documents de mapping.
+                Notez que le <literal>SchemaValidator</literal> dépends de l'API metadata de JDBC, il ne fonctionnera
+                donc pas avec tous les drivers JDBC. Cet outil est extrêmement utile pour tester.
+            </para>
+
+            <para>
+                <literal>java -cp </literal><emphasis>hibernate_classpaths</emphasis>
+                <literal>org.hibernate.tool.hbm2ddl.SchemaValidator</literal> <emphasis>options mapping_files</emphasis>
+            </para>
+
+            <table frame="topbot">
+                <title><literal>SchemaValidator</literal> Options de ligne de commande</title>
+                <tgroup cols="2">
+                    <colspec colwidth="1.5*"/>
+                    <colspec colwidth="2*"/>
+                    <thead>
+                        <row>
+                            <entry>Option</entry>
+                            <entry>Description</entry>
+                        </row>
+                    </thead>
+                    <tbody>
+                        <row>
+                            <entry><literal>--naming=eg.MyNamingStrategy</literal></entry>
+                            <entry>Indique une <literal>NamingStrategy</literal></entry>
+                        </row>
+                        <row>
+                            <entry><literal>--properties=hibernate.properties</literal></entry>
+                            <entry>lit les propriétés dela base de données depuis un fichier de propriétés</entry>
+                        </row>
+                        <row>
+                            <entry><literal>--config=hibernate.cfg.xml</literal></entry>
+                            <entry>indique un fichier <literal>.cfg.xml</literal></entry>
+                        </row>
+                     </tbody>
+                </tgroup>
+            </table>
+
+            <para>
+                Vous pouvez inclure <literal>SchemaValidator</literal> dans votre application:
+            </para>
+
+            <programlisting><![CDATA[Configuration cfg = ....;
+new SchemaValidator(cfg).validate();]]></programlisting>
+
+        </sect2>
+
+        </sect2>
+        <sect2 id="toolsetguide-s1-9">
+            <title>Utiliser Ant pour la validation du Schéma</title>
+
+            <para>
+                Vous pouvez appeler <literal>SchemaValidator</literal> depuis le script Ant:
+            </para>
+
+            <programlisting><![CDATA[<target name="schemavalidate">
+    <taskdef name="schemavalidator"
+        classname="org.hibernate.tool.hbm2ddl.SchemaValidatorTask"
+        classpathref="class.path"/>
+    
+    <schemavalidator
+        properties="hibernate.properties">
+        <fileset dir="src">
+            <include name="**/*.hbm.xml"/>
+        </fileset>
+    </schemavalidator>
+</target>]]></programlisting>
+
+        </sect2>
+    </sect1>
+
+</chapter>
+

Copied: core/trunk/documentation/manual/fr-FR/src/main/docbook/content/transactions.xml (from rev 14070, core/trunk/documentation/manual/fr-FR/src/main/docbook/modules/transactions.xml)
===================================================================
--- core/trunk/documentation/manual/fr-FR/src/main/docbook/content/transactions.xml	                        (rev 0)
+++ core/trunk/documentation/manual/fr-FR/src/main/docbook/content/transactions.xml	2007-10-09 18:28:36 UTC (rev 14074)
@@ -0,0 +1,1074 @@
+<?xml version="1.0" encoding="iso-8859-1"?>
+<chapter id="transactions"  revision="2">
+    <title>Transactions et accès concurrents</title>
+
+    <para>
+        L'un des principaux avantages du mécanisme de contrôle des accès concurrents d'Hibernate est qu'il est très
+        facile à comprendre. Hibernate utilise directement les connexions JDBC ainsi que les ressources JTA sans y
+        ajouter davantage de mécanisme de blocage. Nous vous recommandons de vous familiariser avec les spécifications
+        JDBC, ANSI et d'isolement de transaction de la base de données que vous utilisez.
+    </para>
+
+    <para>
+        Hibernate ne vérouille pas vos objets en mémoire. Votre application peut suivre le
+        comportement défini par le niveau d'isolation de vos transactions de base de données.
+        Notez que grâce à la <literal>Session</literal>, qui est aussi un cache de scope transaction, Hibernate
+        fournit des lectures répétées pour les récupération par identifiants et les requêtes
+        d'entités (pas celle de valeurs scalaires).
+    </para>
+    
+    <para>
+        En addition au versionning pour le controle automatique de concurrence, Hibernate fournit
+        une API (mineure) pour le verrouillage perssimiste des enregistrements, en générant
+        une syntaxe <literal>SELECT FOR UPDATE</literal>. Le controle de concurrence optimiste
+        et cette API seront détaillés plus tard dans ce chapitre.
+    </para>
+
+    <para>
+        Nous aborderons la gestion des accès concurrents en discutant de la granularité des objets <literal>Configuration</literal>,
+        <literal>SessionFactory</literal>, et <literal>Session</literal>, ainsi que de certains concepts relatifs à la base de données
+        et aux longues transactions applicatives.
+    </para>
+
+    <sect1 id="transactions-basics" revision="1">
+        <title>Gestion de session et délimitation de transactions</title>
+
+        <para>Il est important de savoir qu'un objet <literal>SessionFactory</literal> est un objet complexe et optimisé pour
+            fonctionner avec les threads(thread- safe). Il est coûteux à créer et est ainsi prévu pour n'être instancié qu?une
+            seule fois via un objet <literal>Configuration</literal> au démarrage de l'application, 
+            et être partagé par tous les threads d'une application.
+        </para>
+
+        <para>Un objet <literal>Session</literal> est relativement simple et n'est threadsafe. Il est également peu
+            coûteux à créer. Il devrait n'être utilisé qu'une seule fois, pour un processus d'affaire ou une unité de
+            travail ou une conversation et ensuite être relâché. Un objet <literal>Session</literal> ne tentera pas 
+            d'obtenir de connexion ( <literal>Connection</literal> ) 
+            JDBC (ou de <literal>Datasource</literal> ) si ce n'est pas nécessaire.             
+        </para>
+
+        <para>Afin de compléter ce tableau, vous devez également penser aux transactions de base de données. Une
+            transaction de base de données se doit d'être la plus courte possible afin de réduire les risques de
+            collision sur des enregistrements verrouillés. De longues transactions à la base de données nuiront à
+            l'extensibilité de vos applications lorsque confrontées à de hauts niveaux de charge. Par conséquent,
+            il n'est jamais bon de maintenir une transaction ouverte pendant la durée de reflexion de l'utilisateur,
+            jusqu'a ce que l'unité de travail soit achevée.
+        </para>
+
+        <para>Maintenant, comment délimiter une unité de travail? Est-ce qu'une instance de <literal>Session</literal> peut avoir une durée
+            de vie dépassant plusieurs transactions à la base de données, ou bien est-ce que celles-ci doivent être liées une à une?
+            Quand faut-il ouvrir et fermer une <literal>Session</literal> ? Comment définir la démarcation de vos transactions à la base de données?
+        </para>
+
+        <sect2 id="transactions-basics-uow" revision="1">
+            <title>Unité de travail</title>
+
+            <para>
+                Il est important de mentionner que d'utiliser un paradigme <emphasis>session-par-operation</emphasis>
+                est un anti-pattern. Autrement dit: n'ouvrez et ne fermez pas la
+                <literal>Session</literal> à chacun de vos accès simples à la base de données dans un même thread! Bien sûr, le même raisonnement
+                s'applique sur la gestion des transactions à la base de données. Les appels à la base de données
+                devraient être faits en ordre et selon une séquence définie. Ils devraient également être regroupés en
+                des unités de travail atomiques. (Notez que l?utilisation d?une connexion auto-commit constitue le même
+                anti-pattern. Ce mode de fonctionnement existe pour les applications émettant des commandes SQL à partir
+                d?une console. Hibernate désengage le mode auto-commit et s'attend à ce qu'un serveur d'applications le
+                fasse également.)
+                Les transactions avec la base de données ne sont jamais optionnelles, toute communication
+                avec une base de données doit se dérouler dans une transaction, peu importe si vous lisez
+                ou écrivez des données. Comme évoqué, le comportement auto-commit pour lire les
+                données devrait être évité, puisque plusieurs petites transactions ne seront jamais
+                aussi efficaces qu'une seule plus grosse clairement définie comme unité de travail.
+                Ce dernier choix et en plus beaucoup plus facile a maintenir et à faire évoluer.
+            </para>
+
+            <para>
+                Le pattern d'utilisation le plus fréquemment rencontré dans des applications clients serveur
+                multi-usagers est le <emphasis>session-per-request</emphasis>
+                (littéralement : Session par requête). Dans ce modèle, la requête d'un client est envoyée à un serveur
+                (Où la couche de persistance est implémentée via Hibernate), une nouvelle
+                <literal>Session</literal> est ouverte et toutes les opérations d'accès à la base de données sont exécutées à l'intérieur de
+                celle-ci. Lorsque le travail est terminé (et que les réponses à envoyer au client ont été préparées), la
+                session est flushée et fermée. Une seule transaction à la base de données peut être utilisée pour répondre
+                à la requête du client. La transaction est démarrée et validée au même moment où la Session est ouverte 
+                et fermée. La relation entre la <literal>Session</literal> et la <literal>Transaction</literal> est donc one-to-one. 
+                Ce modèle permet de répondre parfaitement aux attentes de la grande majorité des
+                applications.
+            </para>
+
+            <para>
+                Le défi réside dans l'implémentation. Hibernate fournit une fonction de gestion de
+                la "session courante" pour simplifier ce pattern. Tout ce que vous devez faire
+                est démarrer une transaction lorsqu'une requête est traitée par le serveur, et
+                la terminer avant que la réponse ne soit envoyée au client. Vous pouvez le faire
+                de la manière que vous voulez, les solutions communes sont un <literal>ServletFilter</literal>, 
+                l'interception via AOP avec une pointcut sur les méthodes de type "service", ou un conteneur
+                avec interception/proxy. Un conteneur EJB est un moyen standard d'implémenter ce genre d'acpect
+                tranverse comme la démarcation des transactions sur les EJBs session, de manière déclarative
+                avec CMT. Si vous décidez d'utiliser la démarcation programmatique des transactions, préferrez
+                l'API Hibernate <literal>Transaction</literal> détaillée plus tard dans ce chapitre, afin de
+                facilité l'utilisation et la portabilité du code.
+            </para>
+
+            <para>
+                Votre application peut accéder la "session courante" pour exécuter une requête
+                en invoquant simplement <literal>sessionFactory.getCurrentSession()</literal> n'importe où
+                et autant de fois que souhaité. Vous obtiendrez toujours une <literal>Session</literal> 
+                dont le scope est la transaction courante avec la base de données. Ceci doit être configuré 
+                soit dans les ressources local ou dans l'environnement JTA, voir <xref linkend="architecture-current-session"/>.
+            </para>
+
+            <para>
+                Il est parfois utile d'étendre le scope d'une <literal>Session</literal> et d'une transaction
+                à la base de données jusqu'à ce que "la vue soit rendue". Ceci est particulièrement
+                utile dans des applications à base de servlet qui utilisent une phase de rendue séparée une fois
+                que la réponse a été préparée. Etendre la transaction avec la base de données jusqu'à la fin du
+                rendering de la vue est aisé si vous implémentez  votre propre intercepteur. Cependant,
+                ce n'est pas facile si vous vous appuyez sur les EJBs avec CMT, puisqu'une transaction sera
+                achevée au retour de la méthode EJB, avant le rendu de la vue. Rendez vous sur le site
+                Hibernate et sur le forum pour des astuces et des exemples sur le pattern
+                <emphasis>Open Session in View</emphasis> pattern..
+             </para>
+        </sect2>
+
+        <sect2 id="transactions-basics-apptx"  revision="1">
+            <title>Longue conversation</title>
+
+            <para>Le paradigme
+                <emphasis>session-per-request</emphasis>
+                n'est pas le seul élément à utiliser dans le design de vos unités de travail. Plusieurs processus
+                d'affaire requièrent toute une série d'interactions avec l'utilisateur, entrelacées d'accès à la base de
+                donnée. Dans une application Web ou une application d'entreprise, il serait inacceptable que la durée de
+                vie d'une transaction s'étale sur plusieurs interactions avec l'usager. Considérez l'exemple suivant:
+            </para>
+
+            <itemizedlist>
+                <listitem>
+                    <para>Un écran s'affiche. Les données vues par l'usager ont été chargées dans l'instance d'un objet
+                        <literal>Session</literal> , dans le cadre d'une transaction de base de données. L'usager est libre de modifier ces objets.
+                    </para>
+                </listitem>
+                <listitem>
+
+                    <para>L'usager clique "Sauvegarder" après 5 minutes et souhaite persister les modifications qu'il a
+                        apportées. Il s'attend à être la seule personne a avoir modifié ces données et qu'aucune
+                        modification conflictuelle ne se soit produite durant ce laps de temps.</para>
+                </listitem>
+            </itemizedlist>
+
+            <para>Ceci s'appelle une unité de travail. Du point de vue de l'utilisateur: une
+                <emphasis>conversation</emphasis> (ou <emphasis>transaction d'application</emphasis>).
+                Il y a plusieurs façon de mettre ceci en place dans votre application.
+            </para>
+
+            <para>Une première implémentation naïve pourrait consister à garder la
+                <literal>Session</literal> et la transaction à la base de données ouvertes durant le temps de travail de l'usager, à maintenir les
+                enregistrements verrouillés dans la base de données afin d'éviter des modifications concurrentes et de
+                maintenir l'isolation et l'atomicité de la transaction de l'usager. Ceci est un anti-pattern à éviter,
+                puisque le verrouillage des enregistrements dans la base de données ne permettrait pas à l'application
+                de gérer un grand nombre d'usagers concurrents.
+            </para>
+
+            <para>Il apparaît donc évident qu'il faille utiliser plusieurs transactions BDD afin d'implémenter la
+                conversation. Dans ce cas, maintenir l'isolation des processus d'affaire devient
+                partiellement la responsabilité de la couche applicative. Ainsi, la durée de vie d'une conversation
+                devrait englober celle d'une ou de plusieurs transactions de base de données. Celle-ci sera
+                atomique seulement si l'écriture des données mises à jour est faite exclusivement par la dernière
+                transaction BDD la composant. Toutes les autres sous transactions BD ne doivent faire que la lecture de
+                données. Ceci est relativement facile à mettre en place, surtout avec l'utilisation de certaines
+                fonctionnalités d'Hibernate:
+            </para>
+
+            <itemizedlist>
+                <listitem>
+                    <para>
+                        <emphasis>Versionnage Automatique</emphasis>
+                        - Hibernate peut gérer automatiquement les accès concurrents de manière optimiste et détecter si
+                        une modification concurrente s'est produite durant le temps de réflexion d'un usager.
+                    </para>
+                </listitem>
+                <listitem>
+                    <para>
+                        <emphasis>Objets Détachés</emphasis>
+                        - Si vous décidez d'utiliser le paradigme
+                        <emphasis>session-par-requête</emphasis>
+                        discuté plus haut, toutes les entités chargées en mémoire deviendront des objets détachés durant
+                        le temps de réflexion de l'usager. Hibernate vous permet de rattacher ces objets et de persister
+                        les modifications y ayant été apportées. Ce pattern est appelé:
+                        <emphasis>session-per- request-with-detached-objects</emphasis>
+                        (littéralement: session- par-requête-avec-objets-détachés). Le versionnage automatique est
+                        utilisé afin d'isoler les modifications concurrentes.
+                    </para>
+                </listitem>
+                <listitem>
+                    <para>
+                        <emphasis>Session Longues (conversation)</emphasis>
+                        - Une
+                        <literal>Session</literal> Hibernate peut être déconnectée de la couche JDBC sous-jacente après que commit() ait été appelé
+                        sur une transaction à la base de données et reconnectée lors d'une nouvelle requête-client. Ce
+                        pattern s'appelle:
+                        <emphasis>session-per-conversation</emphasis>
+                        (Littéralement: session-par- conversation) et rend superflu le rattachement des
+                        objets. Le versionnage automatique est utilisé afin d'isoler les modifications concurrentes.
+                    </para>
+                </listitem>
+            </itemizedlist>
+
+            <para>Les deux patterns
+                <emphasis>session-per-request-with- detached- objects</emphasis>
+                (session-par-requête-avec-objets- détachés) et
+                <emphasis>session-per-conversation</emphasis>
+                (session-par-conversation) ont chacun leurs avantages et désavantages qui seront exposés
+                dans ce même chapitre, dans la section au sujet du contrôle optimiste de concurrence.
+            </para>
+
+        </sect2>
+
+        <sect2 id="transactions-basics-identity">
+            <title>L'identité des objets</title>
+
+            <para>Une application peut accéder à la même entité persistante de manière concurrente dans deux
+                <literal>Session</literal> s différentes. Toutefois, une instance d'une classe persistante n'est jamais partagée par deux instances
+                distinctes de la classe
+                <literal>Session</literal> . Il existe donc deux notions de l'identité d'un objet:
+            </para>
+
+            <variablelist spacing="compact">
+                <varlistentry>
+                    <term>Identité BD</term>
+                    <listitem>
+                        <para>
+                            <literal>foo.getId().equals( bar.getId() )</literal> </para>
+                    </listitem>
+                </varlistentry>
+                <varlistentry>
+                    <term>Identité JVM</term>
+                    <listitem>
+                        <para>
+                            <literal>foo==bar</literal> </para>
+                    </listitem>
+                </varlistentry>
+            </variablelist>
+
+            <para>Ainsi, pour des objets attachés à une
+                <literal>Session</literal> <emphasis>précise</emphasis>
+                (dans la cadre d'exécution (scope) d'une instance de
+                <literal>Session</literal> ), ces deux notions d'identité sont équivalentes et garanties par Hibernate. Par contre, si une
+                application peut accéder de manière concurrente à la même entité persistante dans deux sessions
+                différentes, les deux instances seront en fait différentes (en ce qui a trait à l'identité JVM). Les
+                conflits sont résolus automatiquement par approche optimiste grâce au système de versionnage automatique
+                lorsque
+                <literal>Session.flush()</literal> ou
+                <literal>Transaction.commit()</literal> est appelé.
+            </para>
+
+            <para>Cette approche permet de reléguer à Hibernate et à la base de données sous-jacente le soin de gérer
+                les problèmes d'accès concurrents. Cette manière de faire assure également une meilleure extensibilité
+                de l'application puisque assurer l'identité JVM dans un thread ne nécessite pas de mécanismes de
+                verrouillage coûteux ou d'autres dispositifs de synchronisation. Une application n'aura jamais le besoin
+                de synchroniser des objets d'affaire tant qu'elle peut garantir qu'un seul thread aura accès à une
+                instance de
+                <literal>Session</literal> . Dans le cadre d'exécution d'un objet
+                <literal>Session</literal> , l'application peut utiliser en toute sécurité <literal>==
+            </literal> pour comparer des objets.
+        </para>
+
+        <para>
+            Une application qui utiliserait <literal>==</literal> à l'extérieur du cadre d'exécution d'une <literal>Session</literal> 
+            pourrait obtenir des résultats inattendus et causer certains effets de bords. Par exemple, si vous mettez 2
+            objets dans le même <literal>Set</literal> , ceux-ci pourraient avoir la même identité BD (i.e. ils représentent le même enregistrement), mais leur
+            identité JVM pourrait être différente (elle ne peut, par définition, pas être garantie sur deux objets
+            détachés). Le développeur doit donc redéfinir l'implémentation des méthodes <literal>equals()</literal> et <literal>hashcode()</literal> 
+            dans les classes persistantes et y adjoindre sa propre notion d'identité. Il existe toutefois une
+            restriction: Il ne faut jamais utiliser uniquement l'identifiant de la base de données dans l'implémentation
+            de l'égalité; Il faut utiliser une clé d'affaire, généralement une combinaison de plusieurs attributs
+            uniques, si possible immuables. Les identifiants de base de données vont changer si un objet transitoire
+            (transient) devient persistant. Si une instance transitoire est contenue dans un <literal>Set</literal> ,
+            changer le hashcode brisera le contrat du <literal>Set</literal> . Les attributs pour les clés d'affaire 
+            n'ont pas à être aussi stables que des clés primaires de bases de
+            données. Il suffit simplement qu'elles soient stables tant et aussi longtemps que les objets sont dans le
+            même <literal>Set</literal> . Veuillez consulter le site web Hibernate pour des discussions plus pointues à ce sujet. Notez que ce
+            concept n'est pas propre à Hibernate mais bien général à l'implémentation de l'identité et de l'égalité en
+            Java.
+        </para>
+    </sect2>
+
+
+    <sect2 id="transactions-basics-issues">
+        <title>Problèmes communs</title>
+
+        <para>Bien qu'il puisse y avoir quelques rares exceptions à cette règle, il est recommandé de ne jamais utiliser
+            les anti-patterns
+            <emphasis>session-per- user-session</emphasis>
+            et
+            <emphasis>session-per-application</emphasis>
+            . Vous trouverez ici- bas quelques problèmes que vous risquez de rencontrer si vous en faite l?utilisation.
+            (Ces problèmes pourraient quand même survenir avec des patterns recommandés) Assurez-vous de bien comprendre
+            les implications de chacun des patterns avant de prendre votre décision.
+        </para>
+
+        <itemizedlist>
+            <listitem>
+                <para>L'objet
+                    <literal>Session</literal> n?est pas conçu pour être utilisé par de multiples threads. En conséquence, les objets
+                    potentiellement multi-thread comme les requêtes HTTP, les EJB Session et Swing Worker, risquent de
+                    provoquer des conditions de course dans la
+                    <literal>Session</literal> si celle-ci est partagée. Dans un environnement web classique, il serait préférable de synchroniser
+                    les accès à la session http afin d?éviter qu?un usager ne recharge une page assez rapidement pour
+                    que deux requêtes s?exécutant dans des threads concurrents n?utilisent la même
+                    <literal>Session</literal> .
+                </para>
+            </listitem>
+            <listitem>
+                <para>Lorsque Hibernate lance une exception, le roll back de la transaction en cours doit être effectué
+                    et la
+                    <literal>Session</literal> doit être immédiatement fermée. (Ceci sera exploré plus tard dans le chapitre.) Si la
+                    <literal>Session</literal> est directement associée à une application, il faut arrêter l?application. Le roll back de la
+                    transaction ne remettra pas les objets dans leur état du début de la transaction. Ainsi, ceux-ci
+                    pourraient être désynchronisés d?avec les enregistrements. (Généralement, cela ne cause pas de réels
+                    problèmes puisque la plupart des exceptions sont non traitables et requièrent la reprise du
+                    processus d?affaire ayant échoué.)
+                </para>
+            </listitem>
+            <listitem>
+                <para>La
+                    <literal>Session</literal> met en mémoire cache tous les objets persistants (les objets surveillés et dont l'état est géré par
+                    Hibernate.) Si la
+                    <literal>Session</literal> est ouverte indéfiniment ou si une trop grande quantité d'objets y est chargée, l?utilisation de la
+                    mémoire peut potentiellement croître jusqu?à atteindre le maximum allouable à l?application
+                    (java.lang.OutOfMemoryError.) Une solution à ce problème est d?appeler les méthodes
+                    <literal>Session.clear()</literal> et
+                    <literal>Session.evict()</literal> pour gérer la mémoire cache de la
+                    <literal>Session</literal> . Vous pouvez également utiliser des stored procedures si vous devez lancer des traitements sur de
+                    grandes quantités d?informations. Certaines solutions sont décrites ici :
+                    <xref linkend="batch"/>
+                    . Garder une
+                    <literal>Session</literal> ouverte pour toute la durée d?une session usager augmente également considérablement le risque de
+                    travailler avec de l?information périmée.
+                </para>
+            </listitem>
+        </itemizedlist>
+
+    </sect2>
+</sect1>
+
+<sect1 id="transactions-demarcation">
+    <title>Démarcation des transactions</title>
+
+    <para>La démarcation des transactions est importante dans le design d?une application. Aucune communication avec la
+        base de données ne peut être effectuée à l?extérieur du cadre d?une transaction. (Il semble que ce concept soit
+        mal compris par plusieurs développeurs trop habitués à utiliser le mode auto-commit.) Même si certains niveaux
+        d'isolation et certaines possibilités offertes par les bases de données permettent de l?éviter, il n'est jamais
+        désavantageux de toujours explicitement indiquer les bornes de transaction pour les opérations complexes comme
+        pour les opérations simples de lecture.</para>
+
+    <para>Une application utilisant Hibernate peut s'exécuter dans un environnement léger n?offrant pas la gestion
+        automatique des transactions (application autonome, application web simple ou applications Swing) ou dans un
+        environnement J2EE offrant des services de gestion automatique des transactions JTA. Dans un environnement
+        simple, Hibernate a généralement la responsabilité de la gestion de son propre pool de connexions à la base de
+        données. Le développeur de l'application doit manuellement délimiter les transactions. En d'autres mots, il
+        appartient au développeur de gérer les appels à
+        <literal>Transaction.begin()</literal>
+        ,
+        <literal>Transaction.commit()</literal>
+        et
+        <literal>Transaction.rollback()</literal>
+        . Un environnement transactionnel J2EE (serveur d'application J2EE) doit offrir la gestion des transactions au
+        niveau du container J2EE. Les bornes de transaction peuvent normalement être définies de manière déclarative
+        dans les descripteurs de déploiement d'EJB Session, par exemple. La gestion programmatique des transactions n'y
+        est donc pas nécessaire. Même les appels à
+        <literal>Session.flush()</literal>
+        sont faits automatiquement.
+    </para>
+
+    <para>Il peut être requis d'avoir une couche de persistance portable. Hibernate offre donc une API appelée
+        <literal>Transaction</literal>
+        qui sert d'enveloppe pour le système de transaction natif de l'environnement de déploiement. Il n'est pas
+        obligatoire d'utiliser cette API mais il est fortement conseillé de le faire, sauf lors de l'utilisation de CMT
+        Session Bean (EJB avec transactions gérées automatiquement par le container EJB).
+    </para>
+
+    <para>Il existe quatre étapes disctinctes lors de la fermeture d'une
+        <literal>Session</literal>
+    </para>
+
+    <itemizedlist spacing="compact">
+        <listitem>
+            <para>flush de la session</para>
+        </listitem>
+        <listitem>
+            <para>commit de la transaction</para>
+        </listitem>
+        <listitem>
+            <para>Fermeture de la session (Close)</para>
+        </listitem>
+        <listitem>
+            <para>Gestion des exceptions</para>
+        </listitem>
+    </itemizedlist>
+
+    <para>La synchronisation de bdd depuis la session (flush) a déjà été expliqué, nous nous attarderons maintenant à la démarcation des
+        transactions et à la gestion des exceptions dans les environnements légers et les environnements J2EE.</para>
+
+
+    <sect2 id="transactions-demarcation-nonmanaged"  revision="2">
+        <title>Environnement non managé</title>
+
+        <para>
+            Si la couche de persistance Hibernate s'exécute dans un environnement non managé, les connexions à la base de
+            données seront généralement prises en charge par le mécanisme de pool d'Hibernate. La gestion de la session
+            et de la transaction se fera donc de la manière suivante:</para>
+
+            <programlisting><![CDATA[// Non-managed environment idiom
+Session sess = factory.openSession();
+Transaction tx = null;
+try {
+    tx = sess.beginTransaction();
+
+    // do some work
+    ...
+
+    tx.commit();
+}
+catch (RuntimeException e) {
+    if (tx != null) tx.rollback();
+    throw e; // or display error message
+}
+finally {
+    sess.close();
+}]]></programlisting>
+
+            <para>
+                Vous n'avez pas à invoquer <literal>flush()</literal> explicitement sur la <literal>Session</literal> -
+                l'appel de <literal>commit()</literal> déclenchera automatiquement la synchronisation (selon le <xref linkend="objectstate-flushing">FlushMode</xref> 
+                de la session. Un appel à <literal>close()</literal> marque la fin de la session.
+                La conséquence directe est que la connexion à la base de données sera relachée par la session.
+                Ce code est portable est fonctionne dans les environnements non managé ET les environnements JTA.
+            </para>
+
+           <para>
+                Une solution plus flexible est la gestion par contexte fourni par Hibernate que nous avons
+                déjà rencontré:
+            </para>
+
+            <programlisting><![CDATA[// Non-managed environment idiom with getCurrentSession()
+try {
+    factory.getCurrentSession().beginTransaction();
+
+    // do some work
+    ...
+
+    factory.getCurrentSession().getTransaction().commit();
+}
+catch (RuntimeException e) {
+    factory.getCurrentSession().getTransaction().rollback();
+    throw e; // or display error message
+}]]></programlisting>
+
+            <para>
+                Vous ne verrez probablement jamais ces exemples de code dans les applications;
+                les exceptions fatales (exceptions du système) ne devraient être traitées que
+                dans la couche la plus "haute". En d'autres termes, le code qui exécute les appels
+                à Hibernate (à la couche de persistance) et le code qui gère les
+                <literal>RuntimeException</literal> (qui ne peut généralement effectuer qu'un nettoyage et une sortie) 
+                sont dans des couches différentes. La gestion du contexte courant par Hibernate peut
+                simplifier notablement ce design, puisque vous devez accéder à la gestion des exceptions
+                de la <literal>SessionFactory</literal>, ce qui est décrit plus tard dans ce chapitre.
+            </para>
+
+           <para>
+                Notez que vous devriez sélectionner <literal>org.hibernate.transaction.JDBCTransactionFactory</literal>
+                (le défaut), pour le second exemple <literal>"thread"</literal> comme
+                <literal>hibernate.current_session_context_class</literal>.
+            </para>
+
+    </sect2>
+
+    <sect2 id="transactions-demarcation-jta" revision="2">
+        <title>Utilisation de JTA</title>
+
+        <para>Si votre couche de persistance s'exécute dans un serveur d'application (par exemple, derrière un EJB
+            Session Bean), toutes les datasource utilisées par Hibernate feront automatiquement partie de transactions
+            JTA globales. Hibernate propose deux stratégies pour réussir cette intégration.</para>
+
+        <para>
+            Si vous utilisez des transactions gérées par un EJB (bean managed transactions - BMT), Hibernate informera
+            le serveur d'application du début et de la fin des transactions si vous utilisez l'API <literal>Transaction</literal> . 
+            Ainsi, le code de gestion des transactions sera identique dans les deux types d'environnements.
+        </para>
+
+           <programlisting><![CDATA[// BMT idiom
+Session sess = factory.openSession();
+Transaction tx = null;
+try {
+    tx = sess.beginTransaction();
+
+    // do some work
+    ...
+
+    tx.commit();
+}
+catch (RuntimeException e) {
+    if (tx != null) tx.rollback();
+    throw e; // or display error message
+}
+finally {
+    sess.close();
+}]]></programlisting>
+
+        <para>Ou encore, avec la gestion automatique de contexte:</para>
+
+            <programlisting><![CDATA[// BMT idiom with getCurrentSession()
+try {
+    factory.getCurrentSession().beginTransaction();
+
+    // do some work
+    ...
+
+    factory.getCurrentSession().getTransaction().commit();
+}
+catch (RuntimeException e) {
+    factory.getCurrentSession().getTransaction().rollback();
+    throw e; // or display error message
+}]]></programlisting>
+
+        <para>
+            Avec CMT, la démarcation des transactions est faite dans les descripteurs de déploiement des Beans Sessions et non
+            de manière programmmatique, ceci réduit le code:
+        </para>
+        
+        <programlisting><![CDATA[// CMT idiom
+ Session sess = factory.getCurrentSession();
+
+ // do some work
+ ...
+]]></programlisting>
+        
+        <para>
+            Dans un EJB CMT même le rollback intervient automatiquement, puisqu'une <literal>RuntimeException</literal>
+            non traitée et soulevée par une méthode d'un bean session indique au conteneur d'annuler la transaction
+            globale. <emphasis>Ceci veut donc dire que vous n'avez pas à utiliser l'API <literal>Transaction</literal> d'Hibernate
+            dans CMT.</emphasis>
+        </para>
+       
+        <para>
+            Notez que le fichier de configuration Hibernate devrait contenir les valeurs 
+            <literal>org.hibernate.transaction.JTATransactionFactory</literal> dans un environnement BMT ou 
+            <literal>org.hibernate.transaction.CMTTransactionFactory</literal> dans un environnement CMT là  où vous
+            configurez votre transaction factory Hibernate. 
+            N'oubliez pas non plus de spécifier le paramètre <literal>org.hibernate.transaction.manager_lookup_class</literal> .
+            De plus, assurez vous de fixez votre <literal>hibernate.current_session_context_class</literal> soit à <literal>"jta"</literal>
+            ou de ne pas le configurer (compatibilité avec les versions précédentes).
+        </para>
+
+        <para>
+            La méthode <literal>getCurrentSession()</literal> a un inconvénient dans les environnement JTA.
+            Il y a une astuce qui est d'utiliser un mode de libération de connexion <literal>after_statement</literal> ,
+            qui est alors utilisé par défaut. Du à une étrange limitation de la spec JTA, il n'est pas possible
+            pour Hibernate de nettoyer et ferme automatiquement un <literal>ScrollableResults</literal> ouvert
+            ou une instance d'<literal>Iterator</literal> retournés <literal>scroll()</literal> ou
+            <literal>iterate()</literal>. Vous <emphasis>devez</emphasis> libérer le curseur base de données
+            sous jacent ou invoquer <literal>Hibernate.close(Iterator)</literal> explicitement depuis un
+            bloc <literal>finally</literal>. (Bien sur, la plupart des applications peuvent éviter
+            d'uiliser <literal>scroll()</literal> ou <literal>iterate()</literal> dans un code CMT.)
+        </para>
+
+    </sect2>
+
+    <sect2 id="transactions-demarcation-exceptions">
+        <title>Gestion des exceptions</title>
+
+        <para>
+            Si une <literal>Session</literal> lance une exception (incluant les exceptions du type <literal>SQLException</literal> 
+            ou d'un sous-type), vous devez immédiatement faire le rollback de la transaction, appeler <literal>Session.close()</literal> 
+            et relâcher les références sur l'objet <literal>Session</literal> . La <literal>Session</literal> contient des méthodes 
+            pouvant la mettre dans un état inutilisable. Vous devez considérer qu'<emphasis>aucune</emphasis>
+            exception lancée par Hibernate n'est traitable. Assurez-vous de fermer la session en faisant l'appel à 
+            <literal>close()</literal> dans un bloc <literal>finally</literal> .
+        </para>
+
+        <para>
+            L'exception <literal>HibernateException</literal> , qui englobe la plupart des exceptions pouvant survenir dans la 
+            couche de persistance Hibernate, est une exception non vérifiée (Ceci n'était pas le cas dans certaines versions antérieures de Hibernate.) Il est de
+            notre avis que nous ne devrions pas forcer un développeur à gérer une exception qu'il ne peut de toute façon
+            pas traiter dans une couche technique. Dans la plupart des applications, les exceptions non vérifiées et les
+            exceptions fatales sont gérées en amont du processus (dans les couches hautes) et un message d'erreur est
+            alors affiché à l'usager (ou un traitement alternatif est invoqué.) Veuillez noter qu'Hibernate peut
+            également lancer des exceptions non vérifiées d'un autre type que <literal>HibernateException</literal> . Celles-ci sont 
+            également non traitables et vous devez les traiter comme telles.
+        </para>
+
+        <para>
+            Hibernate englobe les <literal>SQLException</literal> s lancées lors des interactions directes avec la base de données 
+            dans des exceptions de type: <literal>JDBCException</literal> . En fait, Hibernate essaiera de convertir l'exception dans 
+            un sous-type plus significatif de <literal>JDBCException</literal> . L'exception <literal>SQLException</literal> sous-jacente 
+            est toujours disponible via la méthode <literal>JDBCException.getCause()</literal> . Cette conversion est faite par un objet 
+            de type <literal>SQLExceptionConverter</literal> , qui est rattaché à l'objet <literal>SessionFactory</literal> . 
+            Par défaut, le <literal>SQLExceptionConverter</literal> est associé au dialecte de BD configuré dans Hibernate. Toutefois, 
+            il est possible de fournir sa propre implémentation de l'interface. (Veuillez vous référer à la javadoc sur la classe 
+            <literal>SQLExceptionConverterFactory</literal> pour plus de détails. Les sous-types standard de <literal>JDBCException</literal> sont:
+        </para>
+
+        <itemizedlist spacing="compact">
+            <listitem>
+                <para>
+                    <literal>JDBCConnectionException</literal> - Indique une erreur de communication avec la couche JDBC sous-jacente.
+                </para>
+            </listitem>
+            <listitem>
+                <para>
+                    <literal>SQLGrammarException</literal> - Indique un problème de grammaire ou de syntaxe avec la requête SQL envoyée.
+                </para>
+            </listitem>
+            <listitem>
+                <para>
+                    <literal>ConstraintViolationException</literal> - Indique une violation de contrainte d'intégrité.
+                </para>
+            </listitem>
+            <listitem>
+                <para>
+                    <literal>LockAcquisitionException</literal> - Indique une erreur de verrouillage lors de l'éxécution de la requête.
+                </para>
+            </listitem>
+            <listitem>
+                <para>
+                    <literal>GenericJDBCException</literal> - Indique une erreur générique JDBC d'une autre catégorie.
+                </para>
+            </listitem>
+        </itemizedlist>
+
+    </sect2>
+
+    <sect2 id="transactions-demarcation-timeout">
+        <title>Timeout de transaction</title>
+
+        <para>L'un des avantages fournis par les environnements transactionnels JTA (tels les containers EJB) est la
+            gestion du timeout de transaction. La gestion des dépassements de temps de transaction vise à s'assurer
+            qu'une transaction agissant incorrectement ne viendra pas bloquer indéfiniment les ressources de
+            l'application. Hibernate ne peut fournir cette fonctionnalité dans un environnement transactionnel non-JTA.
+            Par contre, Hibernate gère les opérations d'accès aux données en allouant un temps maximal aux requêtes pour
+            s'exécuter. Ainsi, une requête créant de l'inter blocage ou retournant de très grandes quantités
+            d'information pourrait être interrompue. Dans un environnement transactionnel JTA, Hibernate peut déléguer
+            au gestionnaire de transaction le soin de gérer les dépassements de temps. Cette fonctionnalité est
+            abstraite par l'objet <literal>Transaction</literal> .
+        </para>
+
+        <programlisting><![CDATA[
+        Session sess = factory.openSession();
+        try {
+            //mettre le timeout à 3 secondes.
+            sess.getTransaction().setTimeout(3);
+            sess.getTransaction().begin();
+
+            // Effectuer le travail ...
+
+            sess.getTransaction().commit()
+        }
+        catch (RuntimeException e) {
+            if ( sess.getTransaction().isActive() ) {
+                sess.getTransaction().rollback();
+            }
+            throw e;
+            // ou afficher le message d'erreur.
+        }
+        finally {
+            sess.close();
+        }]]></programlisting>
+
+
+        <para>
+            Notez que <literal>setTimeout()</literal> ne peut pas être appelé d'un EJB CMT, puisque le timeout 
+            des transaction doit être spécifié de manière déclarative.
+        </para>
+
+    </sect2>
+
+</sect1>
+
+<sect1 id="transactions-optimistic">
+    <title>Contrôle de consurrence optimiste</title>
+
+    <para>La gestion optimiste des accès concurrents avec versionnage est la seule approche pouvant garantir
+        l'extensibilité des applications à haut niveau de charge. Le système de versionnage utilise des numéros de
+        version ou l'horodatage pour détecter les mises à jour causant des conflits avec d'autres actualisations
+        antérieures. Hibernate propose trois approches pour l'écriture de code applicatif utilisant la gestion optimiste
+        d'accès concurrents. Le cas d'utilisation décrit plus bas fait mention de conversation,
+        mais le versionnage peut également améliorer la qualité d'une application en prévenant la perte de mises à
+        jour.</para>
+
+    <sect2 id="transactions-optimistic-manual">
+        <title>Gestion du versionnage au niveau applicatif</title>
+
+        <para>Dans cet exemple d'implémentation utilisant peu les fonctionnalités d'Hibernate, chaque interaction avec
+            la base de données se fait en utilisant une nouvelle <literal>Session</literal> et le développeur doit recharger 
+            les données persistantes à partir de la BD avant de les manipuler. Cette
+            implémentation force l'application à vérifier la version des objets afin de maintenir l'isolation
+            transactionnelle. Cette approche, semblable à celle retrouvée pour les EJB, est la moins efficace de celles
+            présentées dans ce chapitre.
+        </para>
+
+        <programlisting>
+            <![CDATA[// foo est une instance chargée antérieurement par une autre
+            Session session = factory.openSession();
+            Transaction t = session.beginTransaction();
+
+            int oldVersion = foo.getVersion();
+            session.load( foo, foo.getKey() ); // Charger l'état courant
+
+            if ( oldVersion != foo.getVersion() )
+                throw new StaleObjectStateException();
+
+            foo.setProperty("bar");
+            t.commit();
+            session.close();]]></programlisting>
+
+        <para>Le mapping de la propriété <literal>version</literal> est fait via <literal>&lt;version&gt;</literal> et 
+        Hibernate l'incrémentera automatiquement à chaque flush() si l'entité doit être mise à jour.
+        </para>
+
+
+        <para>Bien sûr, si votre application ne fait pas face à beaucoup d'accès concurrents et ne nécessite pas
+            l'utilisation du versionnage, cette approche peut également être utilisée, il n'y a qu'à ignorer le code
+            relié au versionnage. Dans ce cas, la stratégie du
+            <emphasis>last commit wins</emphasis>
+            (littéralement: le dernier commit l'emporte) sera utilisée pour les conversations (longues transactions applicatives).
+            Gardez à l'esprit que cette approche pourrait rendre perplexe les utilisateurs de l'application car ils
+            pourraient perdre des données mises à jour sans qu'aucun message d'erreur ne leur soit présenté et sans
+            avoir la possibilité de fusionner les données.
+        </para>
+
+        <para>Il est clair que la gestion manuelle de la vérification du versionnage des objets ne peut être effectuée
+            que dans certains cas triviaux et que cette approche n'est pas valable pour la plupart des applications. De
+            manière générale, les applications ne cherchent pas à actualiser de simples objets sans relations, elles le
+            font généralement pour de larges graphes d'objets. Pour toute application utilisant le paradigme des conversations
+             ou des objets détachés, Hibernate peut gérer automatiquement la vérification des versions
+            d'objets.</para>
+
+    </sect2>
+
+    <sect2 id="transactions-optimistic-longsession">
+        <title>Les sessions longues et le versionnage automatique.</title>
+
+        <para>Dans ce scénario, une seule instance de <literal>Session</literal> et des objets persistants est utilisée 
+            pour toute l'application. Hibernate vérifie la version des objets
+            persistants avant d'effectuer le flush() et lance une exception si une modification concurrente est
+            détectée. Il appartient alors au développeur de gérer l'exception. Les traitements alternatifs généralement
+            proposés sont alors de permettre à l'usager de faire la fusion des données ou de lui offrir de recommencer
+            son travail à partie des données les plus récentes dans la BD.
+        </para>
+
+        <para>Il est à noter que lorsqu'une application est en attente d'une action de la part de l?usager, La <literal>Session</literal> 
+            n'est pas connectée à la couche JDBC sous-jacente. C'est la manière la plus efficace de gérer les accès à la
+            base de données. L'application ne devrait pas se préoccuper du versionnage des objets, de la réassociation
+            des objets détachés, ni du rechargement de tous les objets à chaque transaction.
+        </para>
+
+        <programlisting>
+            <![CDATA[// foo est une instance chargée antérieurement par une autre session
+
+            session.reconnect();// Obtention d'une nouvelle connexion JDBC
+            Transaction t = session.beginTransaction();
+            foo.setProperty("bar");
+            t.commit(); //Terminer la transaction, propager les changements et vérifier les versions.
+            session.disconnect(); // Retourner la connexion JDBC
+            ]]></programlisting>
+
+
+        <para>L'objet <literal>foo</literal> sait quel objet <literal>Session</literal> l'a chargé. <literal>Session.reconnect()</literal> 
+            obtient une nouvelle connexion (celle-ci peut être également fournie) et permet à la session de continuer
+            son travail. La méthode <literal>Session.disconnect()</literal> déconnecte la session de la connexion JDBC et 
+            retourne celle-ci au pool de connexion (à moins que vous ne
+            lui ayez fourni vous même la connexion.) Après la reconnexion, afin de forcer la vérification du versionnage
+            de certaines entités que vous ne cherchez pas à actualiser, vous pouvez faire un appel à <literal>Session.lock()</literal> 
+            en mode <literal>LockMode.READ</literal> pour tout objet ayant pu être modifié par une autre transaction. Il n'est pas nécessaire de verrouiller les
+            données que vous désirez mettre à jour.
+        </para>
+
+        <para>Si des appels implicites aux méthodes <literal>disconnect()</literal> et <literal>reconnect()</literal> sont trop 
+        coûteux, vous pouvez les éviter en utilisant <literal>hibernate.connection.release_mode</literal> .
+        </para>
+
+        <para>Ce pattern peut présenter des problèmes si la <literal>Session</literal> est trop volumineuse pour être 
+            stockée entre les actions de l'usager. Plus spécifiquement, une session <literal>HttpSession</literal> se doit 
+            d'être la plus petite possible. Puisque la <literal>Session</literal> joue obligatoirement le rôle de mémoire 
+            cache de premier niveau et contient à ce titre tous les objets
+            chargés, il est préférable de n'utiliser cette stratégie que pour quelques cycles de requêtes car les objets
+            risquent d'y être rapidement périmés.
+        </para>
+
+        <para>Notez que la <literal>Session</literal> déconnectée devrait être conservée près de la couche de persistance. Autrement dit, utilisez un EJB stateful
+            pour conserver la <literal>Session</literal> et évitez de la sérialiser et de la transférer à la couche de présentation (i.e. Il est préférable de ne pas
+            la conserver dans la session <literal>HttpSession</literal> .)
+        </para>
+
+    </sect2>
+
+    <sect2 id="transactions-optimistic-detached">
+        <title>Les objets détachés et le versionnage automatique</title>
+
+        <para>Chaque interaction avec le système de persistance se fait via une nouvelle <literal>Session</literal> . 
+            Toutefois, les mêmes instances d'objets persistants sont réutilisées pour chacune de ces interactions.
+            L'application doit pouvoir manipuler l'état des instances détachées ayant été chargées antérieurement via
+            une autre session. Pour ce faire, ces objets persistants doivent être rattachés à la <literal>Session</literal> 
+            courante en utilisant <literal>Session.update()</literal> , <literal>Session.saveOrUpdate()</literal> , ou <literal>Session.merge()</literal> .
+        </para>
+
+        <programlisting>
+            <![CDATA[// foo est une instance chargée antérieurement par une autre session
+
+            foo.setProperty("bar");
+            session = factory.openSession();
+            Transaction t = session.beginTransaction();
+            session.saveOrUpdate(foo);  //Utiliser merge() si "foo" pourrait avoir été chargé précédement
+            t.commit();
+            session.close();]]> </programlisting>
+
+
+        <para>Encore une fois, Hibernate vérifiera la version des instances devant être actualisées durant le flush().
+            Une exception sera lancée si des conflits sont détectés.</para>
+
+        <para>Vous pouvez également utiliser <literal>lock()</literal> au lieu de <literal>update()</literal> et 
+            utiliser le mode <literal>LockMode.READ</literal> (qui lancera une vérification de version, en ignorant tous les niveaux de mémoire cache) si vous êtes
+            certain que l'objet n'a pas été modifié.
+        </para>
+
+    </sect2>
+
+    <sect2 id="transactions-optimistic-customizing">
+        <title>Personnaliser le versionnage automatique</title>
+
+        <para>Vous pouvez désactiver l'incrémentation automatique du numéro de version de certains attributs et
+            collections en mettant la valeur du paramètre de mapping <literal>optimistic-lock</literal> à
+            false. Hibernate cessera ainsi d'incrémenter leur numéro de version s'ils sont mis à jour.
+        </para>
+
+        <para>Certaines entreprises possèdent de vieux systèmes dont les schémas de bases de données sont statiques et
+            ne peuvent être modifiés. Il existe aussi des cas où plusieurs applications doivent accéder à la même base
+            de données, mais certaines d'entre elles ne peuvent gérer les numéros de version ou les champs horodatés.
+            Dans les deux cas, le versionnage ne peut être implanté par le rajout d'une colonne dans la base de données.
+            Afin de forcer la vérification de version dans un système sans en faire le mapping, mais en forçant une
+            comparaison des états de tous les attributs d'une entité, vous pouvez utiliser l'attribut <literal>optimistic- lock="all"</literal> 
+            sous l'élément <literal>&lt;class&gt;</literal> . Veuillez noter que cette manière de gérer le versionnage ne peut être utilisée que si l'application
+            utilises de longues sessions, lui permettant de comparer l'ancien état et le nouvel état d'une entité.
+            L'utilisation d'un pattern <literal>session-per-request-with-detached- objects</literal> devient alors impossible.
+        </para>
+
+        <para>Il peut être souhaitable de permettre les modifications concurrentes lorsque des champs distincts sont
+            modifiés. En mettant la propriété <literal>optimistic-lock="dirty"</literal> dans l'élément <literal>&lt;class&gt;</literal> , 
+            Hibernate ne fera la comparaison que des champs devant être actualisés lors du flush().
+        </para>
+
+        <para>Dans les deux cas: en utilisant une colonne de version/horodatée ou via la comparaison de l'état complet
+            de l'objet ou de ses champs modifiés, Hibernate ne créera qu'une seule commande d'UPDATE par entité avec la
+            clause WHERE appropriée pour mettre à jour l'entité
+            <emphasis>ET</emphasis>
+            en vérifier la version. Si vous utilisez la persistance transitive pour propager l'évènement de rattachement
+            à des entités associées, il est possible qu'Hibernate génère des commandes d'UPDATE inutiles. Ceci n'est
+            généralement pas un problème, mais certains déclencheurs
+            <emphasis>on update</emphasis>
+            dans la base de données pourraient être activés même si aucun changement n'était réellement persisté sur des
+            objets associés. Vous pouvez personnaliser ce comportement en indiquant <literal>select-before- update="true"</literal>
+            dans l'élément de mapping <literal>&lt;class&gt;</literal> . Ceci forcera Hibernate à faire le SELECT de l'instance 
+            afin de s'assurer que l'entité doit réellement être
+            actualisée avant de lancer la commande d'UPDATE.
+        </para>
+
+    </sect2>
+
+</sect1>
+
+<sect1 id="transactions-locking">
+    <title>Verouillage pessimiste</title>
+
+    <para>Il n'est nécessaire de s'attarder à la stratégie de verrouillage des entités dans une application utilisant
+        Hibernate. Il est généralement suffisant de définir le niveau d'isolation pour les connexions JDBC et de laisser
+        ensuite la base de donnée effectuer son travail. Toutefois, certains utilisateurs avancés peuvent vouloir
+        obtenir un verrouillage pessimiste exclusif sur un enregistrement et le réobtenir au lancement d'une nouvelle
+        transaction.</para>
+
+    <para>Hibernate utilisera toujours le mécanisme de verrouillage de la base de données et ne verrouillera jamais les
+        objets en mémoire!</para>
+
+    <para>La classe
+        <literal>LockMode</literal>
+        définit les différents niveaux de verrouillage pouvant être obtenus par Hibernate. Le verrouillage est obtenu
+        par les mécanismes suivants:
+    </para>
+
+    <itemizedlist spacing="compact">
+        <listitem>
+            <para>
+                <literal>LockMode.WRITE</literal> est obtenu automatiquement quand Hibernate actualise ou insert un enregistrement.
+            </para>
+        </listitem>
+        <listitem>
+            <para>
+                <literal>LockMode.UPGRADE</literal> peut être obtenu de manière explicite via la requête en utilisant
+                <literal>SELECT ... FOR UPDATE</literal> sur une base de données supportant cette syntaxe.
+            </para>
+        </listitem>
+        <listitem>
+            <para>
+                <literal>LockMode.UPGRADE_NOWAIT</literal> peut être obtenu de manière explicite en utilisant
+                <literal>SELECT ... FOR UPDATE NOWAIT</literal> sur Oracle.
+            </para>
+        </listitem>
+        <listitem>
+            <para>
+                <literal>LockMode.READ</literal> est obtenu automatiquement quand Hibernate lit des données dans un contexte d'isolation
+                <literal>Repeatable Read</literal> ou
+                <literal>Serializable</literal> . Peut être réobtenu explicitement via une requête.
+            </para>
+        </listitem>
+        <listitem>
+            <para>
+                <literal>LockMode.NONE</literal> représente l'absence de verouillage. Tous les objets migrent vers ce mode a la fin d'une
+                <literal>Transaction</literal> . Les objets associés à une session via un appel à
+                <literal>saveOrUpdate()</literal> commencent également leur cycle de vie dans cet état.
+            </para>
+        </listitem>
+    </itemizedlist>
+
+    <para>Les niveaux de verrouillage peuvent être explicitement obtenus de l'une des manières suivantes:</para>
+
+    <itemizedlist spacing="compact">
+        <listitem>
+            <para>Un appel à
+                <literal>Session.load()</literal> , en spécifiant un niveau verrouillage
+                <literal>LockMode</literal> .
+            </para>
+        </listitem>
+        <listitem>
+            <para>Un appel à
+                <literal>Session.lock()</literal> .
+            </para>
+        </listitem>
+        <listitem>
+            <para>Une appel à
+                <literal>Query.setLockMode()</literal> .
+            </para>
+        </listitem>
+    </itemizedlist>
+
+    <para>Si
+        <literal>Session.load()</literal>
+        est appelé avec le paramètre de niveau de verouillage
+        <literal>UPGRADE</literal>
+        ou
+        <literal>UPGRADE_NOWAIT</literal>
+        et que l'objet demandé n'est pas présent dans la session, celui-ci sera chargé à l'aide d'une requête
+        <literal>SELECT ... FOR UPDATE</literal>
+        . Si la méthode
+        <literal>load()</literal>
+        est appelée pour un objet déjà en session avec un verrouillage moindre que celui demandé, Hibernate appellera la
+        méthode
+        <literal>lock()</literal>
+        pour cet objet.
+    </para>
+
+    <para>
+        <literal>Session.lock()</literal>
+        effectue une vérification de version si le niveau de verrouillage est
+        <literal>READ</literal>
+        ,
+        <literal>UPGRADE</literal>
+        ou
+        <literal>UPGRADE_NOWAIT</literal>
+        . (Dans le cas des niveaux
+        <literal>UPGRADE</literal>
+        ou
+        <literal>UPGRADE_NOWAIT</literal>
+        , une requête
+        <literal>SELECT ... FOR UPDATE</literal>
+        sera utilisée.)
+    </para>
+
+    <para>Si une base de données ne supporte pas le niveau de verrouillage demandé, Hibernate utilisera un niveau
+        alternatif convenable au lieux de lancer une exception. Ceci assurera la portabilité de votre
+        application.</para>
+</sect1> 
+
+    <sect1 id="transactions-connection-release">
+        <title>Mode de libération de Connection</title>
+
+        <para>
+            Le comportement original (2.x) d'Hibernate pour la gestion des connexions JDBC
+            était que la <literal>Session</literal> obtenait une connexion dès qu'elle en avait
+            besoin et la libérait une fois la session fermée.
+            Hibernate 3 a introduit les modes de libération de connexion pour indiquer à la session
+            comment gérer les transactions JDBC. Notez que la discussion suivante n'est pertinente 
+            que pour des connexions fournies par un <literal>ConnectionProvider</literal>, celles gérées 
+            par l'utilisateur sont en dehors du scope de cette discussion. Les différents modes
+            sont définies par <literal>org.hibernate.ConnectionReleaseMode</literal>:
+        </para>
+
+        <itemizedlist spacing="compact">
+            <listitem>
+                <para>
+                    <literal>ON_CLOSE</literal> - est essentiellement le comportement passé.
+                    La session Hibernate obtient une connexion lorsqu'elle en a besoin et la garde
+                    jusqu'à ce que la session se ferme.
+                </para>
+            </listitem>
+            <listitem>
+                <para>
+                    <literal>AFTER_TRANSACTION</literal> - indique de relacher la connexion après qu'une
+                    <literal>org.hibernate.Transaction</literal> se soit achevée.
+                </para>
+            </listitem>
+            <listitem>
+                <para>
+                    <literal>AFTER_STATEMENT</literal> (aussi appelé libération brutale) - indique de relacher
+                    les connexions après chaque exécution d'un statement. Ce relachement aggressif est annulé
+                    si ce statement laisse des ressources associées à une session donnée ouvertes, actuellement
+                    ceci n'arrive que lors de l'utilisation de <literal>org.hibernate.ScrollableResults</literal>.
+                </para>
+            </listitem>
+        </itemizedlist>
+
+        <para>
+            Le paramètre de configuration <literal>hibernate.connection.release_mode</literal> est utilisé
+            pour spécifier quel mode de libération doit être utiliser. Les valeurs possibles sont:
+        </para>
+
+        <itemizedlist spacing="compact">
+            <listitem>
+                <para>
+                    <literal>auto</literal> (valeur par défaut) - ce choix délègue le choix de libération
+                    à la méthode <literal>org.hibernate.transaction.TransactionFactory.getDefaultReleaseMode()</literal>
+                    Pour la JTATransactionFactory, elle retourne ConnectionReleaseMode.AFTER_STATEMENT; pour
+                    JDBCTransactionFactory, elle retourne ConnectionReleaseMode.AFTER_TRANSACTION. C'est rarement
+                    une bonne idée de changer ce comportement par défaut puisque les erreurs soulevées par ce
+                    paramétrage tend à prouver une erreur dans le code de l'utilisateur.
+                </para>
+            </listitem>
+            <listitem>
+                <para>
+                    <literal>on_close</literal> - indique d'utiliser ConnectionReleaseMode.ON_CLOSE.  Ce paramétrage
+                    existe pour garantir la compatibilité avec les versions précédentes, mais ne devrait plus être utilisé.
+                </para>
+            </listitem>
+            <listitem>
+                <para>
+                    <literal>after_transaction</literal> - indique d'utiliser ConnectionReleaseMode.AFTER_TRANSACTION.
+                    Ne devrait pas être utilisé dans les environnements JTA. Notez aussi qu'avec 
+                    ConnectionReleaseMode.AFTER_TRANSACTION, si une session est considérée comme étant en mode auto-commit
+                    les connexions seront relachées comme si le mode était AFTER_STATEMENT.
+                </para>
+            </listitem>
+            <listitem>
+                <para>
+                    <literal>after_statement</literal> - indique d'utiliser ConnectionReleaseMode.AFTER_STATEMENT.
+                    Additonnellement, le <literal>ConnectionProvider</literal> utilisé est consulté pour savoir s'il supporte
+                    ce paramétrage (<literal>supportsAggressiveRelease()</literal>). Si ce n'est pas le cas, le mode de
+                    libération est ré initialisé à ConnectionReleaseMode.AFTER_TRANSACTION.  
+                    Ce paramétrage n'est sûr que dans les environnements où il est possible d'obtenir à nouveau
+                    la même connexion JDBC à chaque fois que l'on fait un appel de <literal>ConnectionProvider.getConnection()</literal> 
+                    ou dans les envrionnements auto-commit où il n'est pas important d'obtenir plusieurs fois la 
+                    même connexion.
+                </para>
+            </listitem>
+        </itemizedlist>
+
+    </sect1>
+
+</chapter>
+

Copied: core/trunk/documentation/manual/fr-FR/src/main/docbook/content/tutorial.xml (from rev 14070, core/trunk/documentation/manual/fr-FR/src/main/docbook/modules/tutorial.xml)
===================================================================
--- core/trunk/documentation/manual/fr-FR/src/main/docbook/content/tutorial.xml	                        (rev 0)
+++ core/trunk/documentation/manual/fr-FR/src/main/docbook/content/tutorial.xml	2007-10-09 18:28:36 UTC (rev 14074)
@@ -0,0 +1,1576 @@
+<?xml version="1.0" encoding="iso-8859-1"?>
+<chapter id="tutorial">
+    <title>Introduction à Hibernate</title>
+
+    <sect1 id="tutorial-intro" revision="1">
+        <title>Préface</title>
+
+        <para>
+            Ce chapitre est un didacticiel introductif destiné aux nouveaux utilisateurs
+            d'Hibernate. Nous commençons avec une simple application en ligne de commande
+            utilisant une base de données en mémoire, et la développons en étapes faciles
+            à comprendre.
+        </para>
+
+        <para>
+            Ce didacticiel est destiné aux nouveaux utilisateurs d'Hibernate mais requiert
+            des connaissances Java et SQL. Il est basé sur un didacticiel de Michael Gloegl,
+            les bibliothèques tierces que nous nommons sont pour les JDK 1.4 et 5.0. Vous
+            pourriez avoir besoin d'autres bibliothèques pour le JDK 1.3.
+        </para>
+        
+        <para>
+            Le code source de ce tutoriel est inclus dans la distribution dans le répertoire
+            <literal>doc/reference/tutorial/</literal>.
+        </para>
+
+    </sect1>
+
+    <sect1 id="tutorial-firstapp" revision="1">
+        <title>Partie 1 - Première application Hibernate</title>
+
+        <para>
+            D'abord, nous créerons une simple application Hibernate en console. Nous utilisons
+            une base de données en mémoire (HSQL DB), donc nous n'avons pas à installer de
+            serveur de base de données.
+        </para>
+
+        <para>
+            Supposons que nous ayons besoin d'une petite application de base de données qui
+            puisse stocker des événements que nous voulons suivre, et des informations à propos
+            des hôtes de ces événements.
+        </para>
+
+        <para>
+            La première chose que nous faisons est de configurer notre répertoire de
+            développement et de mettre toutes les bibliothèques dont nous avons besoin dedans.
+            Téléchargez la distribution Hibernate à partir du site web d'Hibernate.
+            Extrayez le paquet et placez toutes les bibliothèques requises trouvées dans
+            <literal>/lib</literal> dans le répertoire <literal>/lib</literal> de votre
+            nouveau répertoire de travail. Il devrait ressembler à ça :
+        </para>
+
+        <programlisting><![CDATA[.
++lib
+  antlr.jar
+  cglib-full.jar
+  asm.jar
+  asm-attrs.jars
+  commons-collections.jar
+  commons-logging.jar
+  ehcache.jar
+  hibernate3.jar
+  jta.jar
+  dom4j.jar
+  log4j.jar ]]></programlisting>
+
+        <para>
+            Ceci est l'ensemble minimum de bibliothèques requises (notez que nous avons aussi
+            copié hibernate3.jar, l'archive principale) pour Hibernate. Lisez le fichier
+            <literal>README.txt</literal> dans le répertoire <literal>lib/</literal> de la
+            distribution Hibernate pour plus d'informations à propos des biliothèques tierces
+            requises et optionnelles. (En fait, log4j n'est pas requis mais préféré par beaucoup
+            de développeurs.)
+        </para>
+
+        <para>
+            Ensuite, nous créons une classe qui réprésente l'événement que nous voulons
+            stocker dans notre base de données.
+        </para>
+
+        <sect2 id="tutorial-firstapp-firstclass" revision="1">
+            <title>La première classe</title>
+
+            <para>
+                Notre première classe persistante est une simple classe JavaBean avec
+                quelques propriétés :
+            </para>
+
+            <programlisting><![CDATA[package events;
+
+import java.util.Date;
+
+public class Event {
+    private Long id;
+
+    private String title;
+    private Date date;
+
+    public Event() {}
+
+    public Long getId() {
+        return id;
+    }
+
+    private void setId(Long id) {
+        this.id = id;
+    }
+
+    public Date getDate() {
+        return date;
+    }
+
+    public void setDate(Date date) {
+        this.date = date;
+    }
+
+    public String getTitle() {
+        return title;
+    }
+
+    public void setTitle(String title) {
+        this.title = title;
+    }
+}]]></programlisting>
+
+            <para>
+                Vous pouvez voir que cette classe utilise les conventions de nommage standard JavaBean
+                pour les méthodes getter/setter des propriétés, ainsi qu'une visibilité privée
+                pour les champs. Ceci est la conception recommandée - mais pas obligatoire. Hibernate peut
+                aussi accéder aux champs directement, le bénéfice des méthodes d'accès est la robustesse
+                pour la refonte de code. Le constructeur sans argument est requis pour instancier
+                un objet de cette classe via reflexion.
+            </para>
+
+            <para>
+                La propriété <literal>id</literal> contient la valeur d'un identifiant unique pour un
+                événement particulier. Toutes les classes d'entités persistantes (ainsi que les classes
+                dépendantes de moindre importance) auront besoin d'une telle propriété identifiante si nous
+                voulons utiliser l'ensemble complet des fonctionnalités d'Hibernate. En fait, la plupart des
+                applications (surtout les applications web) ont besoin de distinguer des objets par des
+                identifiants, donc vous devriez considérer ça comme une fonctionnalité plutôt que comme une
+                limitation. Cependant, nous ne manipulons généralement pas l'identité d'un objet, dorénavant
+                la méthode setter devrait être privée. Seul Hibernate assignera les identifiants lorsqu'un
+                objet est sauvegardé. Vous pouvez voir qu'Hibernate peut accéder aux méthodes publiques,
+                privées et protégées, ainsi qu'aux champs (publics, privés, protégés) directement. Le choix
+                vous est laissé, et vous pouvez l'ajuster à la conception de votre application.
+            </para>
+
+            <para>
+                Le constructeur sans argument est requis pour toutes les classes persistantes ;
+                Hibernate doit créer des objets pour vous en utilisant la réflexion Java. Le
+                constructeur peut être privé, cependant, la visibilité du paquet est requise
+                pour la génération de proxy à l'exécution et une récupération des données efficaces
+                sans instrumentation du bytecode.
+            </para>
+
+            <para>
+                Placez ce fichier source Java dans un répertoire appelé <literal>src</literal>
+                dans le dossier de développement. Ce répertoire devrait maintenant ressembler
+                à ça :
+            </para>
+
+            <programlisting><![CDATA[.
++lib
+  <Hibernate et bibliothèques tierces>
++src
+  +events
+    Event.java]]></programlisting>
+
+
+            <para>
+                Dans la prochaine étape, nous informons Hibernate de cette classe persistante.
+            </para>
+
+        </sect2>
+
+        <sect2 id="tutorial-firstapp-mapping" revision="1">
+            <title>Le fichier de mapping</title>
+
+            <para>
+                Hibernate a besoin de savoir comment charger et stocker des objets d'une classe
+                persistante. C'est là qu'intervient le fichier de mapping Hibernate. Le fichier
+                de mapping indique à Hibernate à quelle table dans la base de données il doit
+                accéder, et quelles colonnes de cette table il devra utiliser.
+            </para>
+
+            <para>
+                La structure basique de ce fichier de mapping ressemble à ça :
+            </para>
+
+            <programlisting><![CDATA[<?xml version="1.0"?>
+<!DOCTYPE hibernate-mapping PUBLIC
+        "-//Hibernate/Hibernate Mapping DTD 3.0//EN"
+        "http://hibernate.sourceforge.net/hibernate-mapping-3.0.dtd">
+
+<hibernate-mapping>
+[...]
+</hibernate-mapping>]]></programlisting>
+
+            <para>
+                Notez que la DTD Hibernate est très sophistiquée. Vous pouvez l'utiliser
+                pour l'auto-complétement des éléments et des attributs de mapping XML dans
+                votre éditeur ou votre IDE. Vous devriez aussi ouvrir le fichier DTD dans
+                votre éditeur de texte - c'est le moyen le plus facile d'obtenir une vue
+                d'ensemble de tous les éléments et attributs, et de voir les valeurs par
+                défaut, ainsi que quelques commentaires. Notez qu'Hibernate ne chargera
+                pas le fichier DTD à partir du web, mais regardera d'abord dans le classpath
+                de l'application. Le fichier DTD est inclus dans <literal>hibernate3.jar</literal>
+                ainsi que dans le répertoire <literal>src</literal> de la distribution
+                Hibernate.
+            </para>
+
+            <para>
+                Nous omettrons la déclaration de la DTD dans les exemples futurs pour
+                raccourcir le code. Bien sûr il n'est pas optionnel.
+            </para>
+
+            <para>
+                Entre les deux balises <literal>hibernate-mapping</literal>, incluez un
+                élément <literal>class</literal>. Toutes les classes d'entités persistantes
+                (encore une fois, il pourrait y avoir des classes dépendantes plus tard,
+                qui ne sont pas des entités mère) ont besoin d'un mapping vers une table
+                de la base de données SQL :
+            </para>
+
+            <programlisting><![CDATA[<hibernate-mapping>
+
+    <class name="Event" table="EVENTS">
+
+    </class>
+
+</hibernate-mapping>]]></programlisting>
+
+            <para>
+                Plus loin, nous disons à Hibernate comment persister et charger un objet de la classe
+                <literal>Event</literal> dans la table <literal>EVENTS</literal>, chaque instance est
+                représentée par une ligne dans cette table. Maintenant nous continuons avec le mapping de
+                la propriété de l'identifiant unique vers la clef primaire de la table. De plus, comme
+                nous ne voulons pas nous occuper de la gestion de cet identifiant, nous utilisons une
+                stratégie de génération d'identifiant d'Hibernate pour la colonne de la clef primaire
+                subrogée :
+            </para>
+
+            <programlisting><![CDATA[<hibernate-mapping>
+
+    <class name="Event" table="EVENTS">
+        <id name="id" column="EVENT_ID">
+            <generator class="increment"/>
+        </id>
+    </class>
+
+</hibernate-mapping>]]></programlisting>
+
+            <para>
+                L'élément <literal>id</literal> est la déclaration de la propriété de l'identifiant,
+                <literal>name="id"</literal> déclare le nom de la propriété Java - Hibernate
+                utilisera les méthodes getter et setter pour accéder à la propriété. L'attribut
+                <literal>column</literal> indique à Hibernate quelle colonne de la table
+                <literal>EVENTS</literal> nous utilisons pour cette clef primaire. L'élément
+                <literal>generator</literal> imbriqué spécifie la stratégie de génération de
+                l'identifiant, dans ce cas nous avons utilisé <literal>increment</literal>,
+                laquelle est une méthode très simple utile surtout pour les tests
+                (et didacticiels). Hibernate supporte aussi les identifiants générés par les
+                bases de données, globalement uniques, ainsi que les identifiants assignés par
+                l'application (ou n'importe quelle stratégie que vous avez écrit en extension).
+            </para>
+
+            <para>
+                Finalement nous incluons des déclarations pour les propriétés persistantes de la classe
+                dans le fichier de mapping. Par défaut, aucune propriété de la classe n'est considérée
+                comme persistante :
+            </para>
+
+            <programlisting><![CDATA[
+<hibernate-mapping>
+
+    <class name="Event" table="EVENTS">
+        <id name="id" column="EVENT_ID">
+            <generator class="increment"/>
+        </id>
+        <property name="date" type="timestamp" column="EVENT_DATE"/>
+        <property name="title"/>
+    </class>
+
+</hibernate-mapping>]]></programlisting>
+
+            <para>
+                Comme avec l'élément <literal>id</literal>, l'attribut <literal>name</literal>
+                de l'élément <literal>property</literal> indique à Hibernate quels getters/setters
+                utiliser.
+            </para>
+
+            <para>
+                Pourquoi le mapping de la propriété <literal>date</literal> inclut
+                l'attribut <literal>column</literal>, mais pas <literal>title</literal> ?
+                Sans l'attribut <literal>column</literal> Hibernate utilise par défaut
+                le nom de la propriété comme nom de colonne. Ca fonctionne bien pour
+                <literal>title</literal>. Cependant, <literal>date</literal> est un mot clef
+                réservé dans la plupart des bases de données, donc nous utilisons un nom
+                différent pour le mapping.
+            </para>
+
+            <para>
+                La prochaine chose intéressante est que le mapping de <literal>title</literal>
+                manque aussi d'un attribut <literal>type</literal>. Les types que nous déclarons
+                et utilisons dans les fichiers de mapping ne sont pas, comme vous pourriez vous
+                y attendre, des types de données Java. Ce ne sont pas, non plus, des types de
+                base de données SQL. Ces types sont donc appelés des <emphasis>types de mapping
+                Hibernate</emphasis>, des convertisseurs qui peuvent traduire des types Java en
+                types SQL et vice versa. De plus, Hibernate tentera de déterminer la bonne conversion
+                et le type de mapping lui-même si l'attribut <literal>type</literal> n'est pas
+                présent dans le mapping. Dans certains cas, cette détection automatique (utilisant
+                la réflexion sur la classe Java) pourrait ne pas donner la valeur attendue ou
+                dont vous avez besoin. C'est le cas avec la propriété <literal>date</literal>.
+                Hibernate ne peut pas savoir si la propriété "mappera" une colonne SQL de type
+                <literal>date</literal>, <literal>timestamp</literal> ou <literal>time</literal>.
+                Nous déclarons que nous voulons conserver des informations avec une date complète
+                et l'heure en mappant la propriété avec un <literal>timestamp</literal>.
+            </para>
+
+            <para>
+                Ce fichier de mapping devrait être sauvegardé en tant que <literal>Event.hbm.xml</literal>,
+                juste dans le répertoire à côté du fichier source de la classe Java <literal>Event</literal>.
+                Le nommage des fichiers de mapping peut être arbitraire, cependant le suffixe
+                <literal>hbm.xml</literal> est devenu une convention dans la communauté des
+                développeurs Hibernate. La structure du répertoire devrait ressembler à ça :
+            </para>
+
+            <programlisting><![CDATA[.
++lib
+  <Hibernate et bibliothèques tierces>
++src
+  Event.java
+  Event.hbm.xml]]></programlisting>
+
+             <para>
+                 Nous poursuivons avec la configuration principale d'Hibernate.
+             </para>
+
+        </sect2>
+
+        <sect2 id="tutorial-firstapp-configuration"  revision="1">
+            <title>Configuration d'Hibernate</title>
+
+            <para>
+                Nous avons maintenant une classe persistante et son fichier de mapping. Il est temps de
+                configurer Hibernate. Avant ça, nous avons besoin d'une base de données. HSQL DB, un
+                SGBD SQL basé sur Java et travaillant en mémoire, peut être téléchargé à partir du site
+                web de HSQL. En fait, vous avez seulement besoin de <literal>hsqldb.jar</literal>. Placez
+                ce fichier dans le répertoire <literal>lib/</literal> du dossier de développement.
+            </para>
+
+            <para>
+                Créez un répertoire appelé <literal>data</literal> à la racine du répertoire de développement - 
+                c'est là que HSQL DB stockera ses fichiers de données. Démarrez maintenant votre base de données
+                en exécutant <literal>java -classpath lib/hsqldb.jar org.hsqldb.Server</literal> dans votre répertoire de travail.
+                Vous observez qu'elle démarre et ouvre une socket TCP/IP, c'est là que notre application
+                se connectera plus tard. Si vous souhaitez démarrez à partir d'une nouvelle base de données
+                pour ce tutoriel (faites <literal>CTRL + C</literal> dans la fenêtre the window), effacez
+                le répertoire <literal>data/</literal> et redémarrez HSQL DB à nouveau.
+                
+            </para>
+
+            <para>
+                Hibernate est la couche de votre application qui se connecte à cette base de données,
+                donc il a besoin des informations de connexion. Les connexions sont établies à travers
+                un pool de connexions JDBC, que nous devons aussi configurer. La distribution Hibernate
+                contient différents outils de gestion de pools de connexions JDBC open source, mais
+                pour ce didacticiel nous utiliserons le pool de connexions intégré à Hibernate. Notez
+                que vous devez copier les bibliothèques requises dans votre classpath et utiliser
+                une configuration de pool de connexions différente si vous voulez utiliser
+                un logiciel de gestion de pools JDBC tiers avec une qualité de production.
+            </para>
+
+            <para>
+                Pour la configuration d'Hibernate, nous pouvons utiliser un simple fichier
+                <literal>hibernate.properties</literal>, un fichier <literal>hibernate.cfg.xml</literal>
+                légèrement plus sophistiqué, ou même une configuration complète par programmation. La
+                plupart des utilisateurs préfèrent le fichier de configuration XML :
+            </para>
+
+            <programlisting><![CDATA[<?xml version='1.0' encoding='utf-8'?>
+<!DOCTYPE hibernate-configuration PUBLIC
+        "-//Hibernate/Hibernate Configuration DTD 3.0//EN"
+        "http://hibernate.sourceforge.net/hibernate-configuration-3.0.dtd">
+
+<hibernate-configuration>
+
+    <session-factory>
+
+        <!-- Database connection settings -->
+        <property name="connection.driver_class">org.hsqldb.jdbcDriver</property>
+        <property name="connection.url">jdbc:hsqldb:hsql://localhost</property>
+        <property name="connection.username">sa</property>
+        <property name="connection.password"></property>
+
+        <!-- JDBC connection pool (use the built-in) -->
+        <property name="connection.pool_size">1</property>
+
+        <!-- SQL dialect -->
+        <property name="dialect">org.hibernate.dialect.HSQLDialect</property>
+
+        <!-- Enable Hibernate's automatic session context management -->
+        <property name="current_session_context_class">thread</property>
+
+        <!-- Disable the second-level cache  -->
+        <property name="cache.provider_class">org.hibernate.cache.NoCacheProvider</property>
+
+        <!-- Echo all executed SQL to stdout -->
+        <property name="show_sql">true</property>
+
+        <!-- Drop and re-create the database schema on startup -->
+        <property name="hbm2ddl.auto">create</property>
+
+        <mapping resource="events/Event.hbm.xml"/>
+
+    </session-factory>
+
+</hibernate-configuration>]]></programlisting>
+            <para>
+                Notez que cette configuration XML utilise une DTD différente. Nous configurons
+                une <literal>SessionFactory</literal> d'Hibernate - une fabrique globale responsable
+                d'une base de données particulière. Si vous avez plusieurs base de données, utilisez
+                plusieurs configurations <literal>&lt;session-factory&gt;</literal>, généralement
+                dans des fichiers de configuration différents (pour un démarrage plus facile).
+            </para>
+
+            <para>
+                Les quatre premiers éléments <literal>property</literal> contiennent la configuration
+                nécessaire pour la connexion JDBC. L'élément <literal>property</literal> du dialecte
+                spécifie quelle variante du SQL Hibernate va générer.  La gestion automatique des sessions
+                d'Hibernate pour les contextes de persistance sera détaillée très vite.
+                L'option <literal>hbm2ddl.auto</literal> active la génération automatique des schémas de
+                base de données - directement dans la base de données. Cela peut bien sûr aussi être
+                désactivé (en supprimant l'option de configuration) ou redirigé vers un fichier avec
+                l'aide de la tâche Ant <literal>SchemaExport</literal>. Finalement, nous ajoutons
+                le(s) fichier(s) de mapping pour les classes persistantes.
+            </para>
+
+            <para>
+                Copiez ce fichier dans le répertoire source, il terminera dans la racine
+                du classpath. Hibernate cherchera automatiquement, au démarrage, un fichier appelé
+                <literal>hibernate.cfg.xml</literal> dans la racine du classpath.
+            </para>
+
+        </sect2>
+
+        <sect2 id="tutorial-firstapp-ant"  revision="1">
+            <title>Construction avec Ant</title>
+
+            <para>
+                Nous allons maintenant construire le didacticiel avec Ant. Vous aurez besoin d'avoir Ant
+                d'installé - récupérez-le à partir de <ulink url="http://ant.apache.org/bindownload.cgi"> la page
+                de téléchargement de Ant</ulink>. Comment installer Ant ne sera pas couvert ici. Référez-vous
+                au <ulink url="http://ant.apache.org/manual/index.html">manuel d'Ant</ulink>. Après que
+                vous aurez installé Ant, nous pourrons commencer à créer le fichier de construction. Il
+                s'appellera <literal>build.xml</literal> et sera placé directement dans le répertoire de
+                développement.
+            </para>
+
+           <para>
+                Un fichier de construction basique ressemble à ça :
+            </para>
+
+            <programlisting><![CDATA[<project name="hibernate-tutorial" default="compile">
+
+    <property name="sourcedir" value="${basedir}/src"/>
+    <property name="targetdir" value="${basedir}/bin"/>
+    <property name="librarydir" value="${basedir}/lib"/>
+
+    <path id="libraries">
+        <fileset dir="${librarydir}">
+            <include name="*.jar"/>
+        </fileset>
+    </path>
+
+    <target name="clean">
+        <delete dir="${targetdir}"/>
+        <mkdir dir="${targetdir}"/>
+    </target>
+
+    <target name="compile" depends="clean, copy-resources">
+      <javac srcdir="${sourcedir}"
+             destdir="${targetdir}"
+             classpathref="libraries"/>
+    </target>
+
+    <target name="copy-resources">
+        <copy todir="${targetdir}">
+            <fileset dir="${sourcedir}">
+                <exclude name="**/*.java"/>
+            </fileset>
+        </copy>
+    </target>
+
+</project>]]></programlisting>
+
+            <para>
+                Cela dira à Ant d'ajouter tous les fichiers du répertoire lib finissant par
+                <literal>.jar</literal> dans le classpath utilisé pour la compilation. Cela copiera aussi
+                tous les fichiers source non Java dans le répertoire cible, par exemple les fichiers de
+                configuration et de mapping d'Hibernate. Si vous lancez Ant maintenant, vous devriez
+                obtenir cette sortie :
+            </para>
+
+            <programlisting><![CDATA[C:\hibernateTutorial\>ant
+Buildfile: build.xml
+
+copy-resources:
+     [copy] Copying 2 files to C:\hibernateTutorial\bin
+
+compile:
+    [javac] Compiling 1 source file to C:\hibernateTutorial\bin
+
+BUILD SUCCESSFUL
+Total time: 1 second ]]></programlisting>
+
+        </sect2>
+
+        <sect2 id="tutorial-firstapp-helpers" revision="3">
+            <title>Démarrage et aides</title>
+
+            <para>
+                Il est temps de charger et de stocker quelques objets <literal>Event</literal>,
+                mais d'abord nous devons compléter la configuration avec du code
+                d'infrastructure. Nous devons démarrer Hibernate. Ce démarrage inclut la construction
+                d'un objet <literal>SessionFactory</literal> global et le stocker quelque part
+                facile d'accès dans le code de l'application. Une <literal>SessionFactory</literal>
+                peut ouvrir des nouvelles <literal>Session</literal>s. Une <literal>Session</literal>
+                représente une unité de travail simplement "threadée", la <literal>SessionFactory</literal>
+                est un objet global "thread-safe", instancié une seule fois.
+            </para>
+
+            <para>
+                Nous créerons une classe d'aide <literal>HibernateUtil</literal> qui s'occupe du
+                démarrage et rend la gestion des <literal>Session</literal>s plus facile. 
+                Regardons l'implémentation :
+            </para>
+
+            <programlisting><![CDATA[package util;
+
+import org.hibernate.*;
+import org.hibernate.cfg.*;
+
+public class HibernateUtil {
+    public static final SessionFactory sessionFactory;
+
+    static {
+        try {
+            // Création de la SessionFactory à partir de hibernate.cfg.xml
+            sessionFactory = new Configuration().configure().buildSessionFactory();
+        } catch (Throwable ex) {
+            // Make sure you log the exception, as it might be swallowed
+            System.err.println("Initial SessionFactory creation failed." + ex);
+            throw new ExceptionInInitializerError(ex);
+        }
+    }
+
+    public static final ThreadLocal session = new ThreadLocal();
+
+    public static SessionFactory getSessionFactory() {
+        return sessionFactory;
+    }
+}]]></programlisting>
+
+            <para>
+                Cette classe ne produit pas seulement la <literal>SessionFactory</literal> globale
+                dans un initialiseur statique (appelé une seule fois par la JVM lorsque la classe
+                est chargée), elle masque le fait qu'elle exploite un singleton. Elle pourrait aussi
+                obtenir la <literal>SessionFactory</literal> depuis JNDI dans un serveur d'applications.
+            </para>
+
+            <para>
+                Si vous nommez la <literal>SessionFactory</literal> dans votre fichier de configuration,
+                Hibernate tentera la récupération depuis JNDI. Pour éviter ce code, vous pouvez aussi
+                utiliser un déploiement JMX et laisser le conteneur (compatible JMX) instancier et lier
+                un <literal>HibernateService</literal> à JNDI. Ces options avancées sont détaillées dans
+                la documentation de référence Hibernate.
+            </para>
+
+            <para>
+                Placez <literal>HibernateUtil.java</literal> dans le répertoire source de développement,
+                et ensuite <literal>Event.java</literal> :
+            </para>
+
+            <programlisting><![CDATA[.
++lib
+  <Hibernate and third-party libraries>
++src
+  +events
+    Event.java
+    Event.hbm.xml
+  +util
+    HibernateUtil.java
+  hibernate.cfg.xml
++data
+build.xml]]></programlisting>
+
+            <para>
+                Cela devrait encore compiler sans problème. Nous avons finalement besoin de configurer
+                le système de "logs" - Hibernate utilise commons-logging et vous laisse le choix entre
+                log4j et le système de logs du JDK 1.4. La plupart des développeurs préfèrent log4j :
+                copiez <literal>log4j.properties</literal> de la distribution d'Hibernate (il est dans
+                le répertoire <literal>etc/</literal>) dans votre répertoire <literal>src</literal>,
+                puis faites de même avec <literal>hibernate.cfg.xml</literal>. Regardez la configuration
+                d'exemple et changez les paramètres si vous voulez une sortie plus verbeuse. Par défaut,
+                seul le message de démarrage d'Hibernate est affiché sur la sortie standard.
+            </para>
+
+            <para>
+                L'infrastructure de ce didacticiel est complète - et nous sommes prêts à effectuer un
+                travail réel avec Hibernate.
+            </para>
+
+        </sect2>
+
+        <sect2 id="tutorial-firstapp-workingpersistence" revision="4">
+            <title>Charger et stocker des objets</title>
+
+            <para>
+                Finalement nous pouvons utiliser Hibernate pour charger et stocker des objets.
+                Nous écrivons une classe <literal>EventManager</literal> avec une méthode
+                <literal>main()</literal> :
+            </para>
+
+            <programlisting><![CDATA[package events;
+import org.hibernate.Session;
+
+import java.util.Date;
+
+import util.HibernateUtil;
+
+public class EventManager {
+
+    public static void main(String[] args) {
+        EventManager mgr = new EventManager();
+
+        if (args[0].equals("store")) {
+            mgr.createAndStoreEvent("My Event", new Date());
+        }
+
+        HibernateUtil.getSessionFactory().close();
+    }
+
+    private void createAndStoreEvent(String title, Date theDate) {
+
+        Session session = HibernateUtil.getSessionFactory().getCurrentSession();
+
+        session.beginTransaction();
+
+        Event theEvent = new Event();
+        theEvent.setTitle(title);
+        theEvent.setDate(theDate);
+
+        session.save(theEvent);
+
+        session.getTransaction().commit();
+    }]]></programlisting>
+
+            <para>
+                Nous créons un nouvel objet <literal>Event</literal>, et le remettons à Hibernate.
+                Hibernate s'occupe maintenant du SQL et exécute les <literal>INSERT</literal>s
+                dans la base de données. Regardons le code de gestion de la <literal>Session</literal>
+                et de la <literal>Transaction</literal> avant de lancer ça.
+            </para>
+
+            <para>
+                Une <literal>Session</literal> est une unité de travail. Pour le moment, nous allons faire
+                les choses simplement et assumer une granularité un-un entre une <literal>Session</literal>
+                hibernate et une transaction à la base de données. Pour isoler notre code du système de transaction
+                sous-jacent (dans notre cas, du pure JDBC, mais cela pourrait être JTA), nous utilisons l'API
+                <literal>Transaction</literal> qui est disponible depuis la <literal>Session</literal> Hibernate.
+            </para>
+
+            <para>
+                Que fait <literal>sessionFactory.getCurrentSession()</literal> ? Premièrement, vous pouvez
+                l'invoquer autant de fois que vous le voulez et n'importe où du moment que vous avez votre
+                <literal>SessionFactory</literal> (facile grâce à <literal>HibernateUtil</literal>). 
+                La méthode <literal>getCurrentSession()</literal> renvoie toujours l'unité de travail courante.
+                Souvenez vous que nous avons basculé notre option de configuration au mécanisme basé sur le "thread"
+                dans <literal>hibernate.cfg.xml</literal>. Par conséquent, le scope de l'unité de travail
+                courante est le thread java courant d'exécution. Ceci n'est pas totalement vrai. Une
+                <literal>Session</literal> commence lorsqu'elle est vraiment utilisée la première fois,
+                Lorsque nous appelons pour la première fois <literal>getCurrentSession()</literal>.
+                Ensuite, elle est liée, par Hibernate, au thread courant. Lorsque la transaction s'achève
+                (commit ou rollback), Hibernate délie la <literal>Session</literal> du thread et la ferme
+                pour vous. Si vous invoquez <literal>getCurrentSession()</literal> une autre fois, vous obtenez
+                une nouvelle <literal>Session</literal> et pouvez entamer une nouvelle unité de travail.
+                Ce modèle de programmation "<emphasis>thread-bound</emphasis>" est le moyen le plus 
+                populaire d'utiliser Hibernate.
+            </para>
+            
+            <para>
+                Lisez <xref linkend="transactions"/> pour plus d'informations sur la gestion des transactions et leur démarcations.
+                Nous n'avons pas géré les erreurs et rollback sur l'exemple précédent.
+            </para>
+
+            <para>
+                Pour lancer cette première routine, nous devons ajouter une cible appelable dans
+                le fichier de construction de Ant :
+            </para>
+
+            <programlisting><![CDATA[<target name="run" depends="compile">
+    <java fork="true" classname="events.EventManager" classpathref="libraries">
+        <classpath path="${targetdir}"/>
+        <arg value="${action}"/>
+    </java>
+</target>]]></programlisting>
+
+            <para>
+                La valeur de l'argument <literal>action</literal> correspond à la ligne de commande
+                qui appelle la cible :
+            </para>
+
+            <programlisting><![CDATA[C:\hibernateTutorial\>ant run -Daction=store]]></programlisting>
+
+            <para>
+                Vous devriez voir, après la compilation, Hibernate démarrer et, en fonction de votre
+                configuration, beaucoup de traces sur la sortie. À la fin vous trouverez la ligne suivante :
+            </para>
+
+            <programlisting><![CDATA[[java] Hibernate: insert into EVENTS (EVENT_DATE, title, EVENT_ID) values (?, ?, ?)]]></programlisting>
+
+            <para>
+                C'est l'<literal>INSERT</literal> exécuté par Hibernate, les points d'interrogation
+                représentent les paramètres JDBC liés. Pour voir les valeurs liées aux arguments, ou
+                pour réduire la verbosité des traces, vérifier votre <literal>log4j.properties</literal>.
+            </para>
+
+            <para>
+                Maintenant nous aimerions aussi lister les événements stockés, donc nous ajoutons une
+                option à la méthode principale :
+            </para>
+
+            <programlisting><![CDATA[if (args[0].equals("store")) {
+    mgr.createAndStoreEvent("My Event", new Date());
+}
+else if (args[0].equals("list")) {
+    List events = mgr.listEvents();
+    for (int i = 0; i < events.size(); i++) {
+        Event theEvent = (Event) events.get(i);
+        System.out.println("Event: " + theEvent.getTitle() +
+                           " Time: " + theEvent.getDate());
+    }
+}]]></programlisting>
+
+            <para>
+                Nous ajoutons aussi une nouvelle méthode <literal>listEvents()</literal> :
+            </para>
+
+            <programlisting><![CDATA[private List listEvents() {
+
+    Session session = HibernateUtil.getSessionFactory().getCurrentSession();
+
+    session.beginTransaction();
+
+    List result = session.createQuery("from Event").list();
+
+    session.getTransaction().commit();
+
+    return result;
+}]]></programlisting>
+
+            <para>
+                Ce que nous faisons ici c'est utiliser une requête HQL (Hibernate Query Language) pour
+                charger tous les objets <literal>Event</literal> existants de la base de données.
+                Hibernate générera le SQL approprié, l'enverra à la base de données et peuplera des
+                objets <literal>Event</literal> avec les données. Vous pouvez créer des requêtes plus
+                complexes avec HQL, bien sûr.
+            </para>
+
+            <para>
+                Maintenant, pour exécuter et tester tout ça, suivez ces étapes :
+            </para>
+
+            <itemizedlist>
+                <listitem>
+                    <para>
+                        Exécutez <literal>ant run -Daction=store</literal> pour stocker quelque
+                        chose dans la base de données et, bien sûr, pour générer, avant, le schéma
+                        de la base de données grâce à hbm2ddl.
+                    </para>
+                </listitem>
+                <listitem>
+                    <para>
+                        Maintenant désactivez hbm2ddl en commentant la propriété dans votre fichier
+                        <literal>hibernate.cfg.xml</literal>. Généralement vous la laissez seulement
+                        activée dans des tests unitaires en continu, mais une autre exécution de hbm2ddl
+                        <emphasis>effacerait</emphasis> tout ce que vous avez stocké - le paramètre de
+                        configuration <literal>create</literal> se traduit en fait par "supprimer toutes les
+                        tables du schéma, puis re-créer toutes les tables, lorsque la SessionFactory est
+                        construite".
+                    </para>
+                </listitem>
+            </itemizedlist>
+
+            <para>
+                Si maintenant vous appelez Ant avec <literal>-Daction=list</literal>, vous devriez voir
+                les événements que vous avez stockés jusque là. Vous pouvez bien sûr aussi appeler l'action
+                <literal>store</literal> plusieurs fois.
+            </para>
+
+        </sect2>
+
+    </sect1>
+
+    <sect1 id="tutorial-associations">
+        <title>Partie 2 - Mapper des associations</title>
+
+        <para>
+            Nous avons mappé une classe d'une entité persistante vers une table. Partons de là et
+            ajoutons quelques associations de classe. D'abord nous ajouterons des gens à notre
+            application, et stockerons une liste d'événements auxquels ils participent.
+        </para>
+
+        <sect2 id="tutorial-associations-mappinguser" revision="1">
+            <title>Mapper la classe Person</title>
+
+            <para>
+                La première version de la classe <literal>Person</literal> est simple :
+            </para>
+
+            <programlisting><![CDATA[package events;
+
+public class Person {
+
+    private Long id;
+    private int age;
+    private String firstname;
+    private String lastname;
+
+    public Person() {}
+
+    // Accessor methods for all properties, private setter for 'id'
+
+}]]></programlisting>
+
+            <para>
+                Créez un nouveau fichier de mapping appelé <literal>Person.hbm.xml</literal> 
+                (n'oubliez pas la référence à la DTD)
+            </para>
+
+            <programlisting><![CDATA[<hibernate-mapping>
+
+    <class name="events.Person" table="PERSON">
+        <id name="id" column="PERSON_ID">
+            <generator class="native"/>
+        </id>
+        <property name="age"/>
+        <property name="firstname"/>
+        <property name="lastname"/>
+    </class>
+
+</hibernate-mapping>]]></programlisting>
+
+            <para>
+                Finalement, ajoutez la nouveau mapping à la configuration d'Hibernate :
+            </para>
+
+            <programlisting><![CDATA[<mapping resource="events/Event.hbm.xml"/>
+<mapping resource="events/Person.hbm.xml"/>]]></programlisting>
+            <para>
+                Nous allons maintenant créer une association entre ces deux entités. Évidemment,
+                des personnes peuvent participer aux événements, et des événements ont des participants.
+                Les questions de conception que nous devons traiter sont : direction, cardinalité et comportement
+                de la collection.
+            </para>
+
+        </sect2>
+
+        <sect2 id="tutorial-associations-unidirset" revision="2">
+            <title>Une association unidirectionnelle basée sur Set</title>
+
+            <para>
+                Nous allons ajouter une collection d'événements à la classe <literal>Person</literal>. De
+                cette manière nous pouvons facilement naviguer dans les événements d'une personne
+                particulière, sans exécuter une requête explicite - en appelant
+                <literal>aPerson.getEvents()</literal>. Nous utilisons une collection Java, un
+                <literal>Set</literal>, parce que la collection ne contiendra pas d'éléments dupliqués et
+                l'ordre ne nous importe pas.
+            </para>
+
+            <para>
+                Nous avons besoin d'une association unidirectionnelle, pluri-valuée, implémentée avec
+                un <literal>Set</literal>. Écrivons le code pour ça dans les classes Java et mappons les :
+            </para>
+
+            <programlisting><![CDATA[public class Person {
+
+    private Set events = new HashSet();
+
+    public Set getEvents() {
+        return events;
+    }
+
+    public void setEvents(Set events) {
+        this.events = events;
+    }
+}]]></programlisting>
+
+            <para>
+                D'abord nous mappons cette association, mais pensez à l'autre côté. Clairement, nous pouvons
+                la laisser unidirectionnelle. Ou alors, nous pourrions créer une autre collection sur
+                <literal>Event</literal>, si nous voulons être capable de la parcourir de manière
+                bidirectionnelle, c'est-à-dire avoir <literal>anEvent.getParticipants()</literal>.
+                Ce n'est pas nécessaire d'un point de vue fonctionnel. Vous pourrez toujours exécuter une requête
+                explicite pour récupérer les participants d'un "event" particulier. Ce choix de conception
+                vous est laissé, mais ce qui reste certains est la cardinalité de l'association: "plusieurs"
+                des deux côtés, nous appelons cela une association <emphasis>many-to-many</emphasis>. 
+                Par conséquent nous utilisons un mapping Hibernate many-to-many:
+            </para>
+
+            <programlisting><![CDATA[<class name="events.Person" table="PERSON">
+    <id name="id" column="PERSON_ID">
+        <generator class="native"/>
+    </id>
+    <property name="age"/>
+    <property name="firstname"/>
+    <property name="lastname"/>
+
+    <set name="events" table="PERSON_EVENT">
+        <key column="PERSON_ID"/>
+        <many-to-many column="EVENT_ID" class="Event"/>
+    </set>
+
+</class>]]></programlisting>
+
+            <para>
+                Hibernate supporte toutes sortes de mapping de collection, un <literal>&lt;set&gt;</literal>
+                étant le plus commun. Pour une association many-to-many (ou une relation
+                d'entité <emphasis>n:m</emphasis>), une table d'association est requise. Chaque ligne dans cette table représente un lien entre une personne et un événement. Le nom de la table est
+                configuré avec l'attribut <literal>table</literal> de l'élément <literal>set</literal>. Le
+                nom de la colonne identifiant dans l'association, du côté de la personne, est défini avec
+                l'élément <literal>&lt;key&gt;</literal>, et le nom de la colonne pour l'événement dans
+                l'attribut <literal>column</literal> de <literal>&lt;many-to-many&gt;</literal>. Vous
+                devez aussi donner à Hibernate la classe des objets de votre collection (c'est-à-dire : la
+                classe de l'autre côté de la collection).
+            </para>
+
+            <para>
+                Le schéma de base de données pour ce mapping est donc :
+            </para>
+
+            <programlisting><![CDATA[
+    _____________        __________________
+   |             |      |                  |       _____________
+   |   EVENTS    |      |   PERSON_EVENT   |      |             |
+   |_____________|      |__________________|      |    PERSON   |
+   |             |      |                  |      |_____________|
+   | *EVENT_ID   | <--> | *EVENT_ID        |      |             |
+   |  EVENT_DATE |      | *PERSON_ID       | <--> | *PERSON_ID  |
+   |  TITLE      |      |__________________|      |  AGE        |
+   |_____________|                                |  FIRSTNAME  |
+                                                  |  LASTNAME   |
+                                                  |_____________|
+ ]]></programlisting>
+
+        </sect2>
+
+        <sect2 id="tutorial-associations-working" revision="1">
+            <title>Travailler avec l'association</title>
+
+            <para>
+                Réunissons quelques personnes et quelques événements dans une nouvelle méthode dans
+                <literal>EventManager</literal> :
+            </para>
+
+            <programlisting><![CDATA[private void addPersonToEvent(Long personId, Long eventId) {
+
+    Session session = HibernateUtil.getSessionFactory().getCurrentSession();
+    session.beginTransaction();
+
+    Person aPerson = (Person) session.load(Person.class, personId);
+    Event anEvent = (Event) session.load(Event.class, eventId);
+
+    aPerson.getEvents().add(anEvent);
+
+    session.getTransaction().commit();
+}]]></programlisting>
+
+            <para>
+                Après le chargement d'une <literal>Person</literal> et d'un <literal>Event</literal>, modifiez
+                simplement la collection en utilisant les méthodes normales de la collection. Comme vous
+                pouvez le voir, il n'y a pas d'appel explicite à <literal>update()</literal> ou
+                <literal>save()</literal>, Hibernate détecte automatiquement que la collection a été
+                modifiée et a besoin d'être mise à jour. Ceci est appelé <emphasis>la vérification sale
+                automatique</emphasis> (NdT : "automatic dirty checking"), et vous pouvez aussi l'essayer en
+                modifiant le nom ou la propriété date de n'importe lequel de vos objets. Tant qu'ils sont dans
+                un état <emphasis>persistant</emphasis>, c'est-à-dire, liés à une <literal>Session</literal> Hibernate
+                particulière (c-à-d qu'ils ont juste été chargés ou sauvegardés dans une unité de travail),
+                Hibernate surveille les changements et exécute le SQL correspondant. Le processus de
+                synchronisation de l'état de la mémoire avec la base de données, généralement seulement à la fin
+                d'une unité de travail, est appelé <emphasis>flushing</emphasis>. Dans notre code, l'unité de travail
+                s'achève par un commit (ou rollback) de la transaction avec la base de données - comme défini 
+                par notre option <literal>thread</literal> de configuration pour la classe <literal>CurrentSessionContext</literal>.
+            </para>
+
+            <para>
+                Vous pourriez bien sûr charger une personne et un événement dans différentes unités de travail. Ou
+                vous modifiez un objet à l'extérieur d'une <literal>Session</literal>, s'il n'est pas dans un état
+                persistant (s'il était persistant avant, nous appelons cet état <emphasis>détaché</emphasis>). 
+                Vous pouvez même modifier une collection lorsqu'elle est détachée:
+            </para>
+
+            <programlisting><![CDATA[private void addPersonToEvent(Long personId, Long eventId) {
+
+    Session session = HibernateUtil.getSessionFactory().getCurrentSession();
+    session.beginTransaction();
+
+    Person aPerson = (Person) session
+            .createQuery("select p from Person p left join fetch p.events where p.id = :pid")
+            .setParameter("pid", personId)
+            .uniqueResult(); // Eager fetch the collection so we can use it detached
+
+    Event anEvent = (Event) session.load(Event.class, eventId);
+
+    session.getTransaction().commit();
+
+    // End of first unit of work
+
+    aPerson.getEvents().add(anEvent); // aPerson (and its collection) is detached
+
+    // Begin second unit of work
+
+    Session session2 = HibernateUtil.getSessionFactory().getCurrentSession();
+    session2.beginTransaction();
+
+    session2.update(aPerson); // Reattachment of aPerson
+
+    session2.getTransaction().commit();
+}]]></programlisting>
+
+            <para>
+                L'appel à <literal>update</literal> rend un objet détaché à nouveau persistant, vous pourriez
+                dire qu'il le lie à une unité de travail, ainsi toutes les modifications (ajout, suppression) que vous avez faites
+                pendant qu'il était détaché peuvent être sauvegardées dans la base de données
+                (il se peut que vous ayez besoin de modifier quelques unes des méthodes précédentes
+                pour retourner cet identifiant).
+            </para>
+
+            <programlisting><![CDATA[else if (args[0].equals("addpersontoevent")) {
+    Long eventId = mgr.createAndStoreEvent("My Event", new Date());
+    Long personId = mgr.createAndStorePerson("Foo", "Bar");
+    mgr.addPersonToEvent(personId, eventId);
+    System.out.println("Added person " + personId + " to event " + eventId);]]></programlisting>
+
+            <para>
+                Ce n'est pas très utile dans notre situation actuelle, mais c'est un concept important
+                que vous pouvez mettre dans votre propre application.
+                Pour le moment, complétez cet exercice en ajoutant une nouvelle action à la méthode
+                principale des <literal>EventManager</literal>s et appelez la à partir de la ligne de
+                commande. Si vous avez besoin des identifiants d'une personne et d'un événement - la
+                méthode <literal>save()</literal> les retourne.
+            </para>
+
+            <para>
+                C'était un exemple d'une association entre deux classes de même importance, deux entités.
+                Comme mentionné plus tôt, il y a d'autres classes et d'autres types dans un modèle typique,
+                généralement "moins importants". Vous en avez déjà vu certains, comme un <literal>int</literal>
+                ou une <literal>String</literal>. Nous appelons ces classes des <emphasis>types de valeur</emphasis>,
+                et leurs instances <emphasis>dépendent</emphasis> d'une entité particulière. Des instances de ces
+                types n'ont pas leur propre identité, elles ne sont pas non plus partagées entre des entités (deux
+                personnes ne référencent pas le même objet <literal>firstname</literal>, même si elles ont le
+                même prénom). Bien sûr, des types de valeur ne peuvent pas seulement être trouvés dans
+                le JDK (en fait, dans une application Hibernate toutes les classes du JDK sont considérées
+                comme des types de valeur), vous pouvez aussi écrire vous-même des classes dépendantes,
+                <literal>Address</literal> ou <literal>MonetaryAmount</literal>, par exemple.
+            </para>
+
+            <para>
+                Vous pouvez aussi concevoir une collection de types de valeur. C'est conceptuellement très
+                différent d'une collection de références vers d'autres entités, mais très ressemblant en Java.
+            </para>
+
+        </sect2>
+
+        <sect2 id="tutorial-associations-valuecollections">
+            <title>Collection de valeurs</title>
+
+            <para>
+                Nous ajoutons une collection d'objets de type de valeur à l'entité <literal>Person</literal>.
+                Nous voulons stocker des adresses email, donc le type que nous utilisons est <literal>String</literal>,
+                et la collection est encore un <literal>Set</literal> :
+            </para>
+            <programlisting><![CDATA[private Set emailAddresses = new HashSet();
+
+public Set getEmailAddresses() {
+    return emailAddresses;
+}
+
+public void setEmailAddresses(Set emailAddresses) {
+    this.emailAddresses = emailAddresses;
+}]]></programlisting>
+
+            <para>
+                Le mapping de ce <literal>Set</literal> :
+            </para>
+
+            <programlisting><![CDATA[<set name="emailAddresses" table="PERSON_EMAIL_ADDR">
+    <key column="PERSON_ID"/>
+    <element type="string" column="EMAIL_ADDR"/>
+</set>]]></programlisting>
+
+            <para>
+                La différence comparée au mapping vu plus tôt est la partie <literal>element</literal>,
+                laquelle dit à Hibernate que la collection ne contient pas de références vers une autre entité,
+                mais une collection d'éléments de type <literal>String</literal> (le nom en minuscule vous
+                indique que c'est un type/convertisseur du mapping Hibernate). Une fois encore, l'attribut
+                <literal>table</literal> de l'élément <literal>set</literal> détermine le nom de la table pour la
+                collection. L'élément <literal>key</literal> définit le nom de la colonne de la clef étrangère
+                dans la table de la collection. L'attribut <literal>column</literal> dans l'élément
+                <literal>element</literal> définit le nom de la colonne où les valeurs de <literal>String</literal>
+                seront réellement stockées.
+            </para>
+
+            <para>
+                Regardons le schéma mis à jour :
+            </para>
+
+            <programlisting><![CDATA[
+  _____________        __________________
+ |             |      |                  |       _____________
+ |   EVENTS    |      |   PERSON_EVENT   |      |             |       ___________________
+ |_____________|      |__________________|      |    PERSON   |      |                   |
+ |             |      |                  |      |_____________|      | PERSON_EMAIL_ADDR |
+ | *EVENT_ID   | <--> | *EVENT_ID        |      |             |      |___________________|
+ |  EVENT_DATE |      | *PERSON_ID       | <--> | *PERSON_ID  | <--> |  *PERSON_ID       |
+ |  TITLE      |      |__________________|      |  AGE        |      |  *EMAIL_ADDR      |
+ |_____________|                                |  FIRSTNAME  |      |___________________|
+                                                |  LASTNAME   |
+                                                |_____________|
+ ]]></programlisting>
+
+            <para>
+                Vous pouvez voir que la clef primaire de la table de la collection est en fait une
+                clef composée, utilisant deux colonnes. Ceci implique aussi qu'il ne peut pas y avoir
+                d'adresses email dupliquées par personne, ce qui est exactement la sémantique dont
+                nous avons besoin pour un ensemble en Java.
+            </para>
+
+            <para>
+                Vous pouvez maintenant tester et ajouter des éléments à cette collection, juste comme
+                nous l'avons fait avant en liant des personnes et des événements. C'est le même code
+                en Java.
+            </para>
+            
+                        <programlisting><![CDATA[private void addEmailToPerson(Long personId, String emailAddress) {
+
+    Session session = HibernateUtil.getSessionFactory().getCurrentSession();
+    session.beginTransaction();
+
+    Person aPerson = (Person) session.load(Person.class, personId);
+
+    // The getEmailAddresses() might trigger a lazy load of the collection
+    aPerson.getEmailAddresses().add(emailAddress);
+
+    session.getTransaction().commit();
+}]]></programlisting>
+
+            <para>
+                Cette fois ci, nous n'avons pas utilisé une requête de chargement agressif (<emphasis>fetch</emphasis>)
+                pour initialiser la collection. Par conséquent, l'invocation du getter déclenchera un
+                select supplémentaire pour l'initialiser. Traquez les logs SQL et tentez d'optimiser
+                ce cas avec un chargement aggressif.
+            </para>
+
+        </sect2>
+
+        <sect2 id="tutorial-associations-bidirectional" revision="1">
+            <title>Associations bidirectionnelles</title>
+
+            <para>
+                Ensuite nous allons mapper une association bidirectionnelle - faire fonctionner
+                l'association entre une personne et un événement à partir des deux côtés en Java.
+                Bien sûr, le schéma de la base de données ne change pas, nous avons toujours une pluralité
+                many-to-many. Une base de données relationnelle est plus flexible qu'un langage de
+                programmation réseau, donc elle n'a pas besoin de direction de navigation - les données
+                peuvent être vues et récupérées de toutes les manières possibles.
+            </para>
+
+            <para>
+                D'abord, ajouter une collection de participants à la classe <literal>Event</literal> :
+            </para>
+
+            <programlisting><![CDATA[private Set participants = new HashSet();
+
+public Set getParticipants() {
+    return participants;
+}
+
+public void setParticipants(Set participants) {
+    this.participants = participants;
+}]]></programlisting>
+
+            <para>
+                Maintenant mapper ce côté de l'association aussi, dans <literal>Event.hbm.xml</literal>.
+            </para>
+
+            <programlisting><![CDATA[<set name="participants" table="PERSON_EVENT" inverse="true">
+    <key column="EVENT_ID"/>
+    <many-to-many column="PERSON_ID" class="events.Person"/>
+</set>]]></programlisting>
+
+            <para>
+                Comme vous le voyez, ce sont des mappings de <literal>set</literal>s normaux dans les
+                deux documents de mapping. Notez que les noms de colonne dans <literal>key</literal> et
+                <literal>many-to-many</literal> sont inversés dans les 2 documents de mapping. L'ajout
+                le plus important ici est l'attribut <literal>inverse="true"</literal> dans l'élément
+                <literal>set</literal> du mapping de la collection des <literal>Event</literal>s.
+            </para>
+
+            <para>
+                Ce que signifie qu'Hibernate devrait prendre l'autre côté - la classe <literal>Person</literal> -
+                s'il a besoin de renseigner des informations à propos du lien entre les deux. Ce sera
+                beaucoup plus facile à comprendre une fois que vous verrez comment le lien bidirectionnel
+                entre les deux entités est créé.
+            </para>
+
+        </sect2>
+
+        <sect2 id="tutorial-associations-usingbidir">
+            <title>Travailler avec des liens bidirectionnels</title>
+
+            <para>
+                Premièrement, gardez à l'esprit qu'Hibernate n'affecte pas la sémantique normale de Java.
+                Comment avons-nous créé un lien entre une <literal>Person</literal> et un <literal>Event</literal>
+                dans l'exemple unidirectionnel ? Nous avons ajouté une instance de <literal>Event</literal>
+                à la collection des références d'événement d'une instance de <literal>Person</literal>. Donc,
+                évidemment, si vous voulons rendre ce lien bidirectionnel, nous devons faire la même chose de
+                l'autre côté - ajouter une référence de <literal>Person</literal> à la collection d'un
+                <literal>Event</literal>. Cette "configuration du lien des deux côtés" est absolument
+                nécessaire et vous ne devriez jamais oublier de le faire.
+            </para>
+
+            <para>
+                Beaucoup de développeurs programment de manière défensive et créent des
+                méthodes de gestion de lien pour affecter correctement les deux côtés,
+                par exemple dans <literal>Person</literal> :
+            </para>
+
+            <programlisting><![CDATA[protected Set getEvents() {
+    return events;
+}
+
+protected void setEvents(Set events) {
+    this.events = events;
+}
+
+public void addToEvent(Event event) {
+    this.getEvents().add(event);
+    event.getParticipants().add(this);
+}
+
+public void removeFromEvent(Event event) {
+    this.getEvents().remove(event);
+    event.getParticipants().remove(this);
+}]]></programlisting>
+
+            <para>
+                Notez que les méthodes get et set pour la collection sont maintenant protégées - ceci permet à des
+                classes du même paquet et aux sous-classes d'accéder encore aux méthodes, mais empêche n'importe qui
+                d'autre de mettre le désordre directement dans les collections (enfin, presque). Vous devriez
+                probablement faire de même avec la collection de l'autre côté.
+            </para>
+
+            <para>
+                Et à propos de l'attribut de mapping <literal>inverse</literal> ? Pour vous, et pour Java, un lien
+                bidirectionnel est simplement une manière de configurer correctement les références des deux côtés.
+                Hibernate n'a cependant pas assez d'informations pour ordonner correctement les expressions SQL
+                <literal>INSERT</literal> et <literal>UPDATE</literal> (pour éviter les violations de contrainte), et
+                a besoin d'aide pour gérer proprement les associations bidirectionnelles. Rendre
+                <literal>inverse</literal> un côté d'une assocation dit à Hibernate de l'ignorer essentiellement, pour
+                le considérer comme un <emphasis>miroir</emphasis> de l'autre côté. C'est tout ce qui est nécessaire à
+                Hibernate pour découvrir tout des problèmes de transformation d'un modèle de navigation
+                directionnelle vers un schéma SQL de base de données. Les règles dont vous devez vous souvenir sont :
+                toutes les associations bidirectionnelles ont besoin d'un côté marqué <literal>inverse</literal>.
+                Dans une association un-vers-plusieurs vous pouvez choisir n'importe quel côté, il n'y a pas de
+                différence.
+            </para>
+<!--
+            <para>
+                In the next section we integrate Hibernate with Tomcat and WebWork - the <literal>EventManager</literal>
+                doesn't scale anymore with our growing application.
+            </para>
+-->
+        </sect2>
+    </sect1>
+    
+    <sect1 id="tutorial-webapp">
+        <title>Part 3 - L'application web EventManager</title>
+
+        <para>
+            Une application web Hibernate utilise la <literal>Session</literal> et <literal>Transaction</literal>
+            comme une application standalone. Cependant, quelques patterns sont utiles. Nous allons coder une
+            <literal>EventManagerServlet</literal>. Cette servlet peut lister tous les évènements stockés dans
+            la base de données, et fournir une formulaire HTML pour saisir d'autres évènements.
+        </para>
+
+        <sect2 id="tutorial-webapp-servlet">
+            <title>Ecrire la servlet de base</title>
+
+            <para>
+                Créons une nouvelle classe dans notre répertoire source, dans le package <literal>events</literal>:
+            </para>
+
+            <programlisting><![CDATA[package events;
+
+// Imports
+
+public class EventManagerServlet extends HttpServlet {
+
+    private final SimpleDateFormat dateFormatter =
+                            new SimpleDateFormat("dd.MM.yyyy");
+
+    // Servlet code
+}]]></programlisting>
+
+            <para>
+                Le <literal>dateFormatter</literal> est un outil que nous utiliserons plus tard pour convertir les objets
+                <literal>Date</literal> depuis et vers des chaines de caractères. Il est propice de n'avoir qu'un
+                formatter comme membre de la servlet.
+            </para>
+
+            <para>
+                La servlet n'accepte que les requêtes HTTP <literal>GET</literal>, la méthode à implémenter est donc
+				<literal>doGet()</literal>:
+            </para>
+
+            <programlisting><![CDATA[protected void doGet(HttpServletRequest request,
+                     HttpServletResponse response)
+        throws ServletException, IOException {
+
+    try {
+        // Begin unit of work
+        HibernateUtil.getSessionFactory()
+                .getCurrentSession().beginTransaction();
+
+        // Process request and render page...
+
+        // End unit of work
+        HibernateUtil.getSessionFactory()
+                .getCurrentSession().getTransaction().commit();
+
+    } catch (Exception ex) {
+        HibernateUtil.getSessionFactory()
+                .getCurrentSession().getTransaction().rollback();
+        throw new ServletException(ex);
+    }
+
+}]]></programlisting>
+
+            <para>
+                La pattern que nous utilisons ici est appelé <emphasis>session-per-request</emphasis>.
+                Lorsqu'une requête touche la servlet, une nouvelle <literal>Session</literal> hibernate est
+                ouverte à l'invocationde <literal>getCurrentSession()</literal> sur la
+                <literal>SessionFactory</literal>. Ensuite, une transaction avec la base de données est démarrée&mdash;
+                tous les accès à la base de données interviennent au sein de la transactiton, peu importe que les données
+                soient lues ou écrites (nous n'utilisons pas le mode auto-commit dans les applications).
+            </para>
+
+            <para>
+                Ensuite, les actions possibles de la requêtes sont exécutées et la réponse HTML
+                est rendue. Nous en parlerons plus tard.
+            </para>
+
+            <para>
+                Enfin, l'unité de travail s'achève lorsque l'exécution et le rendu sont achevés.
+                Si un problème survient lors de ces deux phases, une exception est soulevée et la
+                transaction avec la base de données subit un rollback. Voila pour le pattern
+                <literal>session-per-request</literal>. Au lieu d'un code de démarcation de transaction
+                au sein de chaque servlet, vous pouvez écrire un filtre de servlet.
+                Voir le site Hibernate et le Wiki pour plus d'information sur ce pattern, appelé
+				<emphasis>Open Session in View</emphasis>&mdash; vous en aurez besoin dès que vous
+				utiliserez des JSPs et non plus des servlets pour le rendu de vos vues.
+            </para>
+
+        </sect2>
+
+        <sect2 id="tutorial-webapp-processing">
+            <title>Procéder et rendre</title>
+
+            <para>
+                Implémentons l'exécution de la requête et le rendu de la page.                
+            </para>
+
+<programlisting><![CDATA[// Write HTML header
+PrintWriter out = response.getWriter();
+out.println("<html><head><title>Event Manager</title></head><body>");
+
+// Handle actions
+if ( "store".equals(request.getParameter("action")) ) {
+
+    String eventTitle = request.getParameter("eventTitle");
+    String eventDate = request.getParameter("eventDate");
+
+    if ( "".equals(eventTitle) || "".equals(eventDate) ) {
+        out.println("<b><i>Please enter event title and date.</i></b>");
+    } else {
+        createAndStoreEvent(eventTitle, dateFormatter.parse(eventDate));
+        out.println("<b><i>Added event.</i></b>");
+    }
+}
+
+// Print page
+printEventForm(out);
+listEvents(out);
+
+// Write HTML footer
+out.println("</body></html>");
+out.flush();
+out.close();]]></programlisting>
+
+            <para>
+                Ce style de code avec un mix de Java et d'HTML ne serait pas scalable 
+                dans une application plus complexe&mdash;gardez à l'esprit que nous ne faisons qu'illustrer
+                les concepts basiques d'Hibernate dans ce tutoriel. Ce code affiche une en tête et un pied de page
+                HTML. Dans cette page, sont affichés un formulaire pour la saisie d'évènements ainsi
+                qu'une liste de tous les évènements de la base de données. La première méthode
+                est triviale est ne fait que sortir de l'HTML:
+            </para>
+
+            <programlisting><![CDATA[private void printEventForm(PrintWriter out) {
+    out.println("<h2>Add new event:</h2>");
+    out.println("<form>");
+    out.println("Title: <input name='eventTitle' length='50'/><br/>");
+    out.println("Date (e.g. 24.12.2009): <input name='eventDate' length='10'/><br/>");
+    out.println("<input type='submit' name='action' value='store'/>");
+    out.println("</form>");
+}]]></programlisting>
+
+            <para>
+                La méthode <literal>listEvents()</literal> utilise la
+                <literal>Session</literal> Hibernate liée au thread courant pour exécuter la
+                requête:
+            </para>
+
+            <programlisting><![CDATA[private void listEvents(PrintWriter out) {
+    List result = HibernateUtil.getSessionFactory()
+                    .getCurrentSession().createCriteria(Event.class).list();
+    if (result.size() > 0) {
+        out.println("<h2>Events in database:</h2>");
+        out.println("<table border='1'>");
+        out.println("<tr>");
+        out.println("<th>Event title</th>");
+        out.println("<th>Event date</th>");
+        out.println("</tr>");
+        for (Iterator it = result.iterator(); it.hasNext();) {
+            Event event = (Event) it.next();
+            out.println("<tr>");
+            out.println("<td>" + event.getTitle() + "</td>");
+            out.println("<td>" + dateFormatter.format(event.getDate()) + "</td>");
+            out.println("</tr>");
+        }
+        out.println("</table>");
+    }
+}]]></programlisting>
+
+            <para>
+                FEnfin, l'action <literal>store</literal> renvoie à la méthode
+                <literal>createAndStoreEvent()</literal>, qui utilise aussi la
+                <literal>Session</literal> du thread courant:
+            </para>
+
+            <programlisting><![CDATA[protected void createAndStoreEvent(String title, Date theDate) {
+    Event theEvent = new Event();
+    theEvent.setTitle(title);
+    theEvent.setDate(theDate);
+
+    HibernateUtil.getSessionFactory()
+                    .getCurrentSession().save(theEvent);
+}]]></programlisting>
+
+            <para>
+                La servlet est faite. Une requête à la servlet sera exécutée par une seule
+                <literal>Session</literal> et <literal>Transaction</literal>. Comme pour une application
+                standalone, Hibernate peut automatiquement lier ces objets au thread courant d'exécution.
+                Cela vous laisse la liberté de séparer votre code en couches et d'accéder à la
+				<literal>SessionFactory</literal> par le moyen que vous voulez.
+				Généralement, vous utiliserez des conceptions plus sophistiquées et déplacerez
+				le code d'accès aux données dans une couche DAO. Voir le wiki Hibernate pour plus
+				d'exemples.
+            </para>
+
+        </sect2>
+
+        <sect2 id="tutorial-webapp-deploy">
+            <title>Déployer et tester</title>
+
+            <para>
+                Pour déployer cette application, vous devez créer une archive Web, un War. Ajoutez
+                la cible Ant suivante dans votre <literal>build.xml</literal>:
+            </para>
+
+<programlisting><![CDATA[<target name="war" depends="compile">
+    <war destfile="hibernate-tutorial.war" webxml="web.xml">
+        <lib dir="${librarydir}">
+          <exclude name="servlet.jar"/>
+        </lib>
+
+        <classes dir="${targetdir}"/>
+    </war>
+</target>]]></programlisting>
+
+            <para>
+                Cette cible créé un fichier nommé <literal>hibernate-tutorial.war</literal>
+                dans le répertoire de votre projet. Elle package les bibliothèques et le descripteur <literal>web.xml</literal>
+                qui est attendu dans le répertoire racine de votre projet:
+            </para>
+
+            <programlisting><![CDATA[<?xml version="1.0" encoding="UTF-8"?>
+<web-app version="2.4"
+    xmlns="http://java.sun.com/xml/ns/j2ee"
+    xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
+    xsi:schemaLocation="http://java.sun.com/xml/ns/j2ee http://java.sun.com/xml/ns/j2ee/web-app_2_4.xsd">
+
+    <servlet>
+        <servlet-name>Event Manager</servlet-name>
+        <servlet-class>events.EventManagerServlet</servlet-class>
+    </servlet>
+
+    <servlet-mapping>
+        <servlet-name>Event Manager</servlet-name>
+        <url-pattern>/eventmanager</url-pattern>
+    </servlet-mapping>
+</web-app>]]></programlisting>
+
+            <para>
+                Avant de compiler et déployer l'application web, notez qu'une bibliothèque supplémentaire
+                est requise: <literal>servlet.jar</literal>. C'est le kit de développement de Servlet Java,
+                si vous ne disposez pas de cette bibliothèque, prenez la sur le 
+                <ulink url="http://java.sun.com/products/servlet/archive.html">site de Sun</ulink> et copiez la
+                dans votre répertoire des bibliothèques. Cependant, elle ne sera utilisée uniquement pour la
+                compilation et sera exclue du paackage WAR.
+            </para>
+
+            <para>
+                Pour construire et déployer, appelez <literal>ant war</literal> dans votre projet et
+                copier le fichier <literal>hibernate-tutorial.war</literal> dans le répertoire <literal>webapp</literal> de tomcat
+                Si vous n'avez pas installé Tomcat, téléchargez le et suivez la notice d'installation. 
+                Vous n'avez pas à modifier la configuration Tomcat pour déployer cette application.
+            </para>
+
+            <para>
+                Une fois l'application déployée et Tomcat lancé, accédez à l'application via
+                <literal>http://localhost:8080/hibernate-tutorial/eventmanager</literal>. 
+                Assurez vous de consulter les traces tomcat pour observer l'initialisation
+                d'Hibernate à la première requête touchant votre servlet (l'initialisation statique dans <literal>HibernateUtil</literal>
+                est invoquée) et pour vérifier qu'aucune exception ne survienne.
+            </para>
+
+        </sect2>
+
+    </sect1>
+
+    <sect1 id="tutorial-summary"  revision="1">
+        <title>Résumé</title>
+
+        <para>
+            Ce didacticiel a couvert les bases de l'écriture d'une simple application Hibernate ainsi qu'une petite application web.
+        </para>
+
+        <para>
+            Si vous êtes déjà confiants avec Hibernate, continuez à parcourir les sujets que vous trouvez
+            intéressants à travers la table des matières de la documentation de référence - les plus
+            demandés sont le traitement transactionnel (<xref linkend="transactions"/>), la performance
+            des récupérations d'information (<xref linkend="performance"/>), ou l'utilisation de l'API
+            (<xref linkend="objectstate"/>) et les fonctionnalités des requêtes (<xref linkend="objectstate-querying"/>).
+        </para>
+
+        <para>
+            N'oubliez pas de vérifier le site web d'Hibernate pour d'autres didacticiels (plus spécialisés).
+        </para>
+
+    </sect1>
+
+</chapter>

Copied: core/trunk/documentation/manual/fr-FR/src/main/docbook/content/xml.xml (from rev 14070, core/trunk/documentation/manual/fr-FR/src/main/docbook/modules/xml.xml)
===================================================================
--- core/trunk/documentation/manual/fr-FR/src/main/docbook/content/xml.xml	                        (rev 0)
+++ core/trunk/documentation/manual/fr-FR/src/main/docbook/content/xml.xml	2007-10-09 18:28:36 UTC (rev 14074)
@@ -0,0 +1,292 @@
+<?xml version="1.0" encoding="iso-8859-1"?>
+<chapter id="xml">
+    <title>Mapping XML</title>
+
+    <para><emphasis>
+        Notez que cette fonctionnalité est expérimentale dans Hibernate 3.0 et
+        est en développement extrêmement actif.
+    </emphasis></para>
+
+    <sect1 id="xml-intro" revision="1">
+        <title>Travailler avec des données XML</title>
+
+        <para>
+            Hibernate vous laisse travailler avec des données XML persistantes de la
+            même manière que vous travaillez avec des POJOs persistants. Un arbre XML
+            peut être vu comme une autre manière de représenter les données relationnelles
+            au niveau objet, à la place des POJOs.
+        </para>
+
+        <para>
+            Hibernate supporte dom4j en tant qu'API pour la manipulation des arbres XML.
+            Vous pouvez écrire des requêtes qui récupèrent des arbres dom4j à partie de la
+            base de données, et avoir toutes les modifications que vous faites sur l'arbre
+            automatiquement synchronisées dans la base de données. Vous pouvez  même prendre
+            un document XML, l'analyser en utilisant dom4j, et l'écrire dans la base de
+            données via les opérations basiques d'Hibernate :
+            <literal>persist(), saveOrUpdate(), merge(), delete(), replicate()</literal>
+            (merge() n'est pas encore supporté).
+        </para>
+
+        <para>
+            Cette fonctionnalité a plusieurs applications dont l'import/export de données,
+            l'externalisation d'entités via JMS ou SOAP et les rapports XSLT.
+        </para>
+
+        <para>
+            Un simple mapping peut être utilisé pour simultanément mapper les propriétés
+            d'une classe et les noeuds d'un document XML vers la base de données, ou,
+            si il n'y a pas de classe à mapper, il peut être utilisé juste pour mapper
+            le XML.
+        </para>
+
+        <sect2 id="xml-intro-mapping">
+            <title>Spécifier le mapping XML et le mapping d'une classe ensemble</title>
+
+            <para>
+                Voici un exemple de mapping d'un POJO et du XML simultanément :
+            </para>
+
+            <programlisting><![CDATA[<class name="Account"
+        table="ACCOUNTS"
+        node="account">
+
+    <id name="accountId"
+            column="ACCOUNT_ID"
+            node="@id"/>
+
+    <many-to-one name="customer"
+            column="CUSTOMER_ID"
+            node="customer/@id"
+            embed-xml="false"/>
+
+    <property name="balance"
+            column="BALANCE"
+            node="balance"/>
+
+    ...
+
+</class>]]></programlisting>
+        </sect2>
+
+        <sect2 id="xml-onlyxml">
+            <title>Spécifier seulement un mapping XML</title>
+
+            <para>
+                Voici un exemple dans lequel il n'y a pas de class POJO :
+            </para>
+
+            <programlisting><![CDATA[<class entity-name="Account"
+        table="ACCOUNTS"
+        node="account">
+
+    <id name="id"
+            column="ACCOUNT_ID"
+            node="@id"
+            type="string"/>
+
+    <many-to-one name="customerId"
+            column="CUSTOMER_ID"
+            node="customer/@id"
+            embed-xml="false"
+            entity-name="Customer"/>
+
+    <property name="balance"
+            column="BALANCE"
+            node="balance"
+            type="big_decimal"/>
+
+    ...
+
+</class>]]></programlisting>
+
+            <para>
+                Ce mapping vous permet d'accéder aux données comme un arbre dom4j, ou comme
+                un graphe de paire nom de propriété/valeur (<literal>Map</literal>s java). Les
+                noms des propriétés sont des constructions purement logiques qui peuvent être
+                référées des dans requêtes HQL.
+            </para>
+
+        </sect2>
+
+     </sect1>
+
+    <sect1 id="xml-mapping" revision="1">
+        <title>Métadonnées du mapping XML</title>
+
+        <para>
+            Plusieurs éléments du mapping Hibernate acceptent l'attribut <literal>node</literal>.
+            Ceci vous permet de spécifier le nom d'un attribut XML ou d'un élément qui
+            contient la propriété ou les données de l'entité. Le format de l'attribut
+            <literal>node</literal> doit être un des suivants :
+        </para>
+
+        <itemizedlist spacing="compact">
+        <listitem>
+            <para><literal>"element-name"</literal> - mappe vers l'élément XML nommé</para>
+        </listitem>
+        <listitem>
+            <para><literal>"@attribute-name"</literal> - mappe vers l'attribut XML nommé</para>
+        </listitem>
+        <listitem>
+            <para><literal>"."</literal> - mappe vers le parent de l'élément</para>
+        </listitem>
+        <listitem>
+            <para>
+                <literal>"element-name/@attribute-name"</literal> -
+                mappe vers l'élément nommé de l'attribut nommé
+            </para>
+        </listitem>
+        </itemizedlist>
+
+        <para>
+            Pour des collections et de simples associations valuées, il y a un attribut
+            <literal>embed-xml</literal> supplémentaire. Si <literal>embed-xml="true"</literal>,
+            qui est la valeur par défaut, l'arbre XML pour l'entité associée (ou la collection
+            des types de valeurs) sera embarquée directement dans l'arbre XML pour l'entité qui
+            possède l'association. Sinon, si <literal>embed-xml="false"</literal>, alors
+            seule la valeur de l'identifiant référencé apparaîtra dans le XML pour de simples
+            associations de points, et les collections n'appraîtront simplement pas.
+        </para>
+
+        <para>
+            Vous devriez faire attention à ne pas laisser <literal>embed-xml="true"</literal>
+            pour trop d'associations, puisque XML ne traite pas bien les liens circurlaires.
+        </para>
+
+        <programlisting><![CDATA[<class name="Customer"
+        table="CUSTOMER"
+        node="customer">
+
+    <id name="id"
+            column="CUST_ID"
+            node="@id"/>
+
+    <map name="accounts"
+            node="."
+            embed-xml="true">
+        <key column="CUSTOMER_ID"
+                not-null="true"/>
+        <map-key column="SHORT_DESC"
+                node="@short-desc"
+                type="string"/>
+        <one-to-many entity-name="Account"
+                embed-xml="false"
+                node="account"/>
+    </map>
+
+    <component name="name"
+            node="name">
+        <property name="firstName"
+                node="first-name"/>
+        <property name="initial"
+                node="initial"/>
+        <property name="lastName"
+                node="last-name"/>
+    </component>
+
+    ...
+
+</class>]]></programlisting>
+
+        <para>
+            dans ce cas, nous avons décidé d'embarquer la collection d'identifiants de compte,
+            mais pas les données actuelles du compte. La requête HQL suivante :
+        </para>
+
+        <programlisting><![CDATA[from Customer c left join fetch c.accounts where c.lastName like :lastName]]></programlisting>
+
+        <para>
+            devrait retourner l'ensemble de données suivant :
+        </para>
+
+        <programlisting><![CDATA[<customer id="123456789">
+    <account short-desc="Savings">987632567</account>
+    <account short-desc="Credit Card">985612323</account>
+    <name>
+        <first-name>Gavin</first-name>
+        <initial>A</initial>
+        <last-name>King</last-name>
+    </name>
+    ...
+</customer>]]></programlisting>
+
+        <para>
+            Si vous positionnez <literal>embed-xml="true"</literal> sur le mapping
+            <literal>&lt;one-to-many&gt;</literal>, les données pourraient
+            ressembler plus à ça :
+        </para>
+
+        <programlisting><![CDATA[<customer id="123456789">
+    <account id="987632567" short-desc="Savings">
+        <customer id="123456789"/>
+        <balance>100.29</balance>
+    </account>
+    <account id="985612323" short-desc="Credit Card">
+        <customer id="123456789"/>
+        <balance>-2370.34</balance>
+    </account>
+    <name>
+        <first-name>Gavin</first-name>
+        <initial>A</initial>
+        <last-name>King</last-name>
+    </name>
+    ...
+</customer>]]></programlisting>
+
+    </sect1>
+
+
+    <sect1 id="xml-manipulation" revision="1">
+        <title>Manipuler des données XML</title>
+
+        <para>
+            Relisons et mettons à jour des documents XML dans l'application. Nous faisons
+            ça en obtenant une session dom4j :
+        </para>
+
+       <programlisting><![CDATA[Document doc = ....;
+
+Session session = factory.openSession();
+Session dom4jSession = session.getSession(EntityMode.DOM4J);
+Transaction tx = session.beginTransaction();
+
+List results = dom4jSession
+    .createQuery("from Customer c left join fetch c.accounts where c.lastName like :lastName")
+    .list();
+for ( int i=0; i<results.size(); i++ ) {
+    //add the customer data to the XML document
+    Element customer = (Element) results.get(i);
+    doc.getRootElement().add(customer);
+}
+
+tx.commit();
+session.close();]]></programlisting>
+
+       <programlisting><![CDATA[Session session = factory.openSession();
+Session dom4jSession = session.getSession(EntityMode.DOM4J);
+Transaction tx = session.beginTransaction();
+
+Element cust = (Element) dom4jSession.get("Customer", customerId);
+for ( int i=0; i<results.size(); i++ ) {
+    Element customer = (Element) results.get(i);
+    //change the customer name in the XML and database
+    Element name = customer.element("name");
+    name.element("first-name").setText(firstName);
+    name.element("initial").setText(initial);
+    name.element("last-name").setText(lastName);
+}
+
+tx.commit();
+session.close();]]></programlisting>
+
+        <para>
+            Il est extrêmement utile de combiner cette fonctionnalité avec l'opération
+            <literal>replicate()</literal> d'Hibernate pour implémenter des imports/exports
+            de données XML.
+        </para>
+
+    </sect1>
+
+</chapter>
+

Added: core/trunk/documentation/manual/fr-FR/src/main/docbook/images/AuthorWork.png
===================================================================
(Binary files differ)


Property changes on: core/trunk/documentation/manual/fr-FR/src/main/docbook/images/AuthorWork.png
___________________________________________________________________
Name: svn:mime-type
   + application/octet-stream

Added: core/trunk/documentation/manual/fr-FR/src/main/docbook/images/AuthorWork.zargo
===================================================================
(Binary files differ)


Property changes on: core/trunk/documentation/manual/fr-FR/src/main/docbook/images/AuthorWork.zargo
___________________________________________________________________
Name: svn:mime-type
   + application/octet-stream

Added: core/trunk/documentation/manual/fr-FR/src/main/docbook/images/CustomerOrderProduct.png
===================================================================
(Binary files differ)


Property changes on: core/trunk/documentation/manual/fr-FR/src/main/docbook/images/CustomerOrderProduct.png
___________________________________________________________________
Name: svn:mime-type
   + application/octet-stream

Added: core/trunk/documentation/manual/fr-FR/src/main/docbook/images/CustomerOrderProduct.zargo
===================================================================
(Binary files differ)


Property changes on: core/trunk/documentation/manual/fr-FR/src/main/docbook/images/CustomerOrderProduct.zargo
___________________________________________________________________
Name: svn:mime-type
   + application/octet-stream

Added: core/trunk/documentation/manual/fr-FR/src/main/docbook/images/EmployerEmployee.png
===================================================================
(Binary files differ)


Property changes on: core/trunk/documentation/manual/fr-FR/src/main/docbook/images/EmployerEmployee.png
___________________________________________________________________
Name: svn:mime-type
   + application/octet-stream

Added: core/trunk/documentation/manual/fr-FR/src/main/docbook/images/EmployerEmployee.zargo
===================================================================
(Binary files differ)


Property changes on: core/trunk/documentation/manual/fr-FR/src/main/docbook/images/EmployerEmployee.zargo
___________________________________________________________________
Name: svn:mime-type
   + application/octet-stream

Added: core/trunk/documentation/manual/fr-FR/src/main/docbook/images/full_cream.png
===================================================================
(Binary files differ)


Property changes on: core/trunk/documentation/manual/fr-FR/src/main/docbook/images/full_cream.png
___________________________________________________________________
Name: svn:mime-type
   + application/octet-stream

Added: core/trunk/documentation/manual/fr-FR/src/main/docbook/images/full_cream.svg
===================================================================
--- core/trunk/documentation/manual/fr-FR/src/main/docbook/images/full_cream.svg	                        (rev 0)
+++ core/trunk/documentation/manual/fr-FR/src/main/docbook/images/full_cream.svg	2007-10-09 18:28:36 UTC (rev 14074)
@@ -0,0 +1,429 @@
+<?xml version="1.0" standalone="no"?>
+<!DOCTYPE svg PUBLIC "-//W3C//DTD SVG 20010904//EN"
+"http://www.w3.org/TR/2001/REC-SVG-20010904/DTD/svg10.dtd"
+[
+ <!ATTLIST svg
+  xmlns:xlink CDATA #FIXED "http://www.w3.org/1999/xlink">
+]>
+<!-- Created with Sodipodi ("http://www.sodipodi.com/") -->
+<svg
+   xmlns="http://www.w3.org/2000/svg"
+   xmlns:xlink="http://www.w3.org/1999/xlink"
+   width="354.331"
+   height="336.614"
+   id="svg1">
+  <defs
+     id="defs3">
+    <linearGradient
+       x1="0"
+       y1="0"
+       x2="1"
+       y2="0"
+       id="linearGradient127"
+       gradientUnits="objectBoundingBox"
+       spreadMethod="pad">
+      <stop
+         style="stop-color:#000000;stop-opacity:1;"
+         offset="0"
+         id="stop128" />
+      <stop
+         style="stop-color:#ffffff;stop-opacity:1;"
+         offset="1"
+         id="stop129" />
+    </linearGradient>
+    <linearGradient
+       x1="0"
+       y1="0"
+       x2="1"
+       y2="0"
+       id="linearGradient130"
+       xlink:href="#linearGradient127"
+       gradientUnits="objectBoundingBox"
+       spreadMethod="pad" />
+    <radialGradient
+       cx="0.5"
+       cy="0.5"
+       fx="0.5"
+       fy="0.5"
+       r="0.5"
+       id="radialGradient131"
+       xlink:href="#linearGradient127"
+       gradientUnits="objectBoundingBox"
+       spreadMethod="pad" />
+  </defs>
+  <g
+     transform="matrix(0.823795,0,0,0.823795,0.120302,5.25349)"
+     style="font-size:12;"
+     id="g659">
+    <rect
+       width="212.257"
+       height="57.2441"
+       x="17.9576"
+       y="100.132"
+       style="fill:#757575;fill-rule:evenodd;stroke-width:1pt;"
+       id="rect137" />
+    <rect
+       width="285.502"
+       height="118.523"
+       x="13.4238"
+       y="95.9309"
+       transform="matrix(0.743454,0,0,0.482981,6.46949,52.2178)"
+       style="fill:#d2d2d2;fill-rule:evenodd;stroke-width:1pt;"
+       id="rect132" />
+  </g>
+  <rect
+     width="325.86"
+     height="63.6537"
+     x="17.4083"
+     y="15.194"
+     style="font-size:12;fill:#757575;fill-rule:evenodd;stroke-width:1pt;"
+     id="rect136" />
+  <rect
+     width="325.86"
+     height="63.6537"
+     x="13.6713"
+     y="12.4966"
+     style="font-size:12;fill:#d2d2d2;fill-rule:evenodd;stroke-width:1pt;"
+     id="rect126" />
+  <g
+     transform="matrix(1.14345,0,0,0.729078,-1.67818,105.325)"
+     style="font-size:12;"
+     id="g164">
+    <rect
+       width="285.502"
+       height="77.2688"
+       x="16.6979"
+       y="222.966"
+       style="fill:#757575;fill-rule:evenodd;stroke-width:1pt;"
+       id="rect138" />
+    <rect
+       width="285.502"
+       height="77.2688"
+       x="14.7335"
+       y="221.002"
+       transform="translate(-1.30962,-1.30992)"
+       style="fill:#d2d2d2;fill-rule:evenodd;stroke-width:1pt;"
+       id="rect133" />
+  </g>
+  <text
+     x="170.824753"
+     y="58.402939"
+     transform="scale(0.823795,0.823795)"
+     style="font-size:18;font-weight:normal;stroke-width:1pt;font-family:Helvetica;"
+     id="text183">
+    <tspan
+       x="170.824997"
+       y="58.402901"
+       id="tspan360">
+Application</tspan>
+  </text>
+  <text
+     x="178.076340"
+     y="364.281433"
+     transform="scale(0.823795,0.823795)"
+     style="font-size:18;font-weight:normal;stroke-width:1pt;font-family:Helvetica;"
+     id="text197">
+    <tspan
+       x="178.076004"
+       y="364.281006"
+       id="tspan421">
+Database</tspan>
+  </text>
+  <text
+     x="68.605331"
+     y="138.524582"
+     transform="scale(0.823795,0.823795)"
+     style="font-size:16;font-weight:normal;stroke-width:1pt;font-family:Helvetica;"
+     id="text216">
+    <tspan
+       x="68.605301"
+       y="138.524994"
+       id="tspan384">
+SessionFactory</tspan>
+  </text>
+  <rect
+     width="67.0014"
+     height="101.35"
+     x="196.927"
+     y="89.2389"
+     style="font-size:12;fill:#757575;fill-rule:evenodd;stroke-width:1pt;"
+     id="rect387" />
+  <rect
+     width="67.0014"
+     height="101.35"
+     x="194.633"
+     y="86.4389"
+     style="font-size:12;fill:#d2d2d2;fill-rule:evenodd;stroke-width:1pt;"
+     id="rect388" />
+  <text
+     x="249.108841"
+     y="173.885559"
+     transform="scale(0.823795,0.823795)"
+     style="font-size:16;font-weight:normal;stroke-width:1pt;font-family:Helvetica;"
+     id="text389">
+    <tspan
+       x="249.108994"
+       y="173.886002"
+       id="tspan392">
+Session</tspan>
+  </text>
+  <rect
+     width="73.0355"
+     height="101.35"
+     x="270.995"
+     y="90.0018"
+     style="font-size:12;fill:#757575;fill-rule:evenodd;stroke-width:1pt;"
+     id="rect395" />
+  <rect
+     width="73.0355"
+     height="101.35"
+     x="267.869"
+     y="87.2018"
+     style="font-size:12;fill:#d2d2d2;fill-rule:evenodd;stroke-width:1pt;"
+     id="rect396" />
+  <text
+     x="328.593658"
+     y="174.715622"
+     transform="scale(0.823795,0.823795)"
+     style="font-size:16;font-weight:normal;stroke-width:1pt;font-family:Helvetica;"
+     id="text397">
+    <tspan
+       x="328.593994"
+       y="174.716003"
+       id="tspan563">
+Transaction</tspan>
+  </text>
+  <g
+     transform="matrix(0.29544,0,0,0.397877,9.70533,103.96)"
+     style="font-size:12;"
+     id="g565">
+    <rect
+       width="285.502"
+       height="118.523"
+       x="16.6979"
+       y="99.2053"
+       style="fill:#757575;fill-rule:evenodd;stroke-width:1pt;"
+       id="rect566" />
+    <rect
+       width="285.502"
+       height="118.523"
+       x="13.4238"
+       y="95.9309"
+       style="fill:#d2d2d2;fill-rule:evenodd;stroke-width:1pt;"
+       id="rect567" />
+  </g>
+  <text
+     x="25.592752"
+     y="204.497803"
+     transform="scale(0.823795,0.823795)"
+     style="font-size:10;font-weight:normal;stroke-width:1pt;font-family:Helvetica;"
+     id="text568">
+    <tspan
+       x="25.592800"
+       y="204.498001"
+       id="tspan662">
+TransactionFactory</tspan>
+  </text>
+  <g
+     transform="matrix(0.298082,0,0,0.397877,99.6898,103.96)"
+     style="font-size:12;"
+     id="g573">
+    <rect
+       width="285.502"
+       height="118.523"
+       x="16.6979"
+       y="99.2053"
+       style="fill:#757575;fill-rule:evenodd;stroke-width:1pt;"
+       id="rect574" />
+    <rect
+       width="285.502"
+       height="118.523"
+       x="13.4238"
+       y="95.9309"
+       style="fill:#d2d2d2;fill-rule:evenodd;stroke-width:1pt;"
+       id="rect575" />
+  </g>
+  <text
+     x="134.030670"
+     y="205.532791"
+     transform="scale(0.823795,0.823795)"
+     style="font-size:10;font-weight:normal;stroke-width:1pt;font-family:Helvetica;"
+     id="text576">
+    <tspan
+       x="134.031006"
+       y="205.533005"
+       id="tspan664">
+ConnectionProvider</tspan>
+  </text>
+  <g
+     transform="matrix(1.14345,0,0,0.729078,-1.67818,38.9539)"
+     style="font-size:12;"
+     id="g587">
+    <rect
+       width="285.502"
+       height="77.2688"
+       x="16.6979"
+       y="222.966"
+       style="fill:#757575;fill-rule:evenodd;stroke-width:1pt;"
+       id="rect588" />
+    <rect
+       width="285.502"
+       height="77.2688"
+       x="14.7335"
+       y="221.002"
+       transform="translate(-1.30962,-1.30992)"
+       style="fill:#d2d2d2;fill-rule:evenodd;stroke-width:1pt;"
+       id="rect589" />
+  </g>
+  <rect
+     width="90.951"
+     height="44.4829"
+     x="25.6196"
+     y="206.028"
+     style="font-size:12;fill:#757575;fill-rule:evenodd;stroke-width:1pt;"
+     id="rect594" />
+  <rect
+     width="90.951"
+     height="44.4829"
+     x="24.4229"
+     y="204.135"
+     style="font-size:12;fill:#b3b3b3;fill-rule:evenodd;stroke-width:1pt;"
+     id="rect595" />
+  <text
+     x="85.575645"
+     y="282.300354"
+     transform="scale(0.823795,0.823795)"
+     style="font-size:18;font-weight:normal;stroke-width:1pt;font-family:Helvetica;text-anchor:middle;"
+     id="text596">
+    <tspan
+       x="85.575600"
+       y="282.299988"
+       id="tspan607">
+JNDI</tspan>
+  </text>
+  <rect
+     width="90.951"
+     height="44.4829"
+     x="236.937"
+     y="206.791"
+     style="font-size:12;fill:#757575;fill-rule:evenodd;stroke-width:1pt;"
+     id="rect610" />
+  <rect
+     width="90.951"
+     height="44.4829"
+     x="235.741"
+     y="204.898"
+     style="font-size:12;fill:#b3b3b3;fill-rule:evenodd;stroke-width:1pt;"
+     id="rect611" />
+  <text
+     x="342.093201"
+     y="283.226410"
+     transform="scale(0.823795,0.823795)"
+     style="font-size:18;font-weight:normal;stroke-width:1pt;font-family:Helvetica;text-anchor:middle;"
+     id="text612">
+    <tspan
+       x="342.092987"
+       y="283.226013"
+       id="tspan621">
+JTA</tspan>
+  </text>
+  <rect
+     width="90.951"
+     height="44.4829"
+     x="130.134"
+     y="206.791"
+     style="font-size:12;fill:#757575;fill-rule:evenodd;stroke-width:1pt;"
+     id="rect616" />
+  <rect
+     width="90.951"
+     height="44.4829"
+     x="128.937"
+     y="204.898"
+     style="font-size:12;fill:#b3b3b3;fill-rule:evenodd;stroke-width:1pt;"
+     id="rect617" />
+  <text
+     x="212.445343"
+     y="283.226410"
+     transform="scale(0.823795,0.823795)"
+     style="font-size:18;font-weight:normal;stroke-width:1pt;font-family:Helvetica;text-anchor:middle;"
+     id="text618">
+    <tspan
+       x="212.445007"
+       y="283.226013"
+       id="tspan623">
+JDBC</tspan>
+  </text>
+  <g
+     transform="matrix(0.823795,0,0,0.823795,0.120302,6.19341)"
+     style="font-size:12;"
+     id="g637">
+    <g
+       transform="matrix(0.499515,0,0,0.415467,-0.237339,5.61339)"
+       id="g167">
+      <rect
+         width="199.065"
+         height="61.5532"
+         x="61.8805"
+         y="68.4288"
+         style="fill:#757575;fill-rule:evenodd;stroke-width:1pt;"
+         id="rect134" />
+      <rect
+         width="199.065"
+         height="61.5532"
+         x="59.2613"
+         y="65.8095"
+         style="fill:#e0e0e0;fill-rule:evenodd;stroke-width:1pt;"
+         id="rect135" />
+    </g>
+    <text
+       x="33.749969"
+       y="50.589706"
+       style="font-size:11;font-weight:normal;stroke-width:1pt;font-family:Helvetica;"
+       id="text188">
+      <tspan
+         x="33.750000"
+         y="50.589699"
+         id="tspan635">
+Transient Objects</tspan>
+    </text>
+  </g>
+  <g
+     transform="matrix(0.823795,0,0,0.823795,0.120302,5.25349)"
+     style="font-size:12;"
+     id="g644">
+    <g
+       transform="matrix(0.297486,0,0,0.516482,230.251,36.9178)"
+       id="g364">
+      <rect
+         width="199.065"
+         height="61.5532"
+         x="61.8805"
+         y="68.4288"
+         style="fill:#757575;fill-rule:evenodd;stroke-width:1pt;"
+         id="rect365" />
+      <rect
+         width="199.065"
+         height="61.5532"
+         x="59.2613"
+         y="65.8095"
+         style="fill:#e0e0e0;fill-rule:evenodd;stroke-width:1pt;"
+         id="rect366" />
+    </g>
+    <text
+       x="277.123230"
+       y="85.155571"
+       style="font-size:11;font-weight:normal;stroke-width:1pt;font-family:Helvetica;text-anchor:middle;"
+       id="text367">
+      <tspan
+         x="277.122986"
+         y="85.155602"
+         id="tspan631">
+Persistent</tspan>
+      <tspan
+         x="277.122986"
+         y="96.155602"
+         id="tspan633">
+Objects</tspan>
+    </text>
+  </g>
+</svg>

Added: core/trunk/documentation/manual/fr-FR/src/main/docbook/images/hibernate_logo_a.png
===================================================================
(Binary files differ)


Property changes on: core/trunk/documentation/manual/fr-FR/src/main/docbook/images/hibernate_logo_a.png
___________________________________________________________________
Name: svn:mime-type
   + application/octet-stream

Added: core/trunk/documentation/manual/fr-FR/src/main/docbook/images/lite.png
===================================================================
(Binary files differ)


Property changes on: core/trunk/documentation/manual/fr-FR/src/main/docbook/images/lite.png
___________________________________________________________________
Name: svn:mime-type
   + application/octet-stream

Added: core/trunk/documentation/manual/fr-FR/src/main/docbook/images/lite.svg
===================================================================
--- core/trunk/documentation/manual/fr-FR/src/main/docbook/images/lite.svg	                        (rev 0)
+++ core/trunk/documentation/manual/fr-FR/src/main/docbook/images/lite.svg	2007-10-09 18:28:36 UTC (rev 14074)
@@ -0,0 +1,334 @@
+<?xml version="1.0" standalone="no"?>
+<!DOCTYPE svg PUBLIC "-//W3C//DTD SVG 20010904//EN"
+"http://www.w3.org/TR/2001/REC-SVG-20010904/DTD/svg10.dtd"
+[
+ <!ATTLIST svg
+  xmlns:xlink CDATA #FIXED "http://www.w3.org/1999/xlink">
+]>
+<!-- Created with Sodipodi ("http://www.sodipodi.com/") -->
+<svg
+   xmlns="http://www.w3.org/2000/svg"
+   xmlns:xlink="http://www.w3.org/1999/xlink"
+   width="318.898"
+   height="248.031"
+   id="svg1">
+  <defs
+     id="defs3">
+    <linearGradient
+       x1="0"
+       y1="0"
+       x2="1"
+       y2="0"
+       id="linearGradient127"
+       gradientUnits="objectBoundingBox"
+       spreadMethod="pad">
+      <stop
+         style="stop-color:#000000;stop-opacity:1;"
+         offset="0"
+         id="stop128" />
+      <stop
+         style="stop-color:#ffffff;stop-opacity:1;"
+         offset="1"
+         id="stop129" />
+    </linearGradient>
+    <linearGradient
+       x1="0"
+       y1="0"
+       x2="1"
+       y2="0"
+       id="linearGradient130"
+       xlink:href="#linearGradient127"
+       gradientUnits="objectBoundingBox"
+       spreadMethod="pad" />
+    <radialGradient
+       cx="0.5"
+       cy="0.5"
+       fx="0.5"
+       fy="0.5"
+       r="0.5"
+       id="radialGradient131"
+       xlink:href="#linearGradient127"
+       gradientUnits="objectBoundingBox"
+       spreadMethod="pad" />
+  </defs>
+  <rect
+     width="291.837"
+     height="57.0074"
+     x="17.3169"
+     y="18.646"
+     style="font-size:12;fill:#757575;fill-rule:evenodd;stroke-width:1pt;"
+     id="rect136" />
+  <rect
+     width="291.837"
+     height="57.0074"
+     x="13.9703"
+     y="16.2302"
+     style="font-size:12;fill:#d2d2d2;fill-rule:evenodd;stroke-width:1pt;"
+     id="rect126" />
+  <g
+     transform="matrix(0.326107,0,0,0.765831,9.59261,8.98517)"
+     style="font-size:12;"
+     id="g161">
+    <rect
+       width="285.502"
+       height="118.523"
+       x="16.6979"
+       y="99.2053"
+       style="fill:#757575;fill-rule:evenodd;stroke-width:1pt;"
+       id="rect137" />
+    <rect
+       width="285.502"
+       height="118.523"
+       x="13.4238"
+       y="95.9309"
+       style="fill:#d2d2d2;fill-rule:evenodd;stroke-width:1pt;"
+       id="rect132" />
+  </g>
+  <g
+     transform="matrix(1.02406,0,0,0.652953,0.223384,39.9254)"
+     style="font-size:12;"
+     id="g164">
+    <rect
+       width="285.502"
+       height="77.2688"
+       x="16.6979"
+       y="222.966"
+       style="fill:#757575;fill-rule:evenodd;stroke-width:1pt;"
+       id="rect138" />
+    <rect
+       width="285.502"
+       height="77.2688"
+       x="14.7335"
+       y="221.002"
+       transform="translate(-1.30962,-1.30992)"
+       style="fill:#d2d2d2;fill-rule:evenodd;stroke-width:1pt;"
+       id="rect133" />
+  </g>
+  <g
+     transform="matrix(0.449834,0,0,0.338463,-3.15909,9.73319)"
+     style="font-size:12;"
+     id="g167">
+    <rect
+       width="199.065"
+       height="61.5532"
+       x="61.8805"
+       y="68.4288"
+       style="fill:#757575;fill-rule:evenodd;stroke-width:1pt;"
+       id="rect134" />
+    <rect
+       width="199.065"
+       height="61.5532"
+       x="59.2613"
+       y="65.8095"
+       style="fill:#e0e0e0;fill-rule:evenodd;stroke-width:1pt;"
+       id="rect135" />
+  </g>
+  <text
+     x="302.277679"
+     y="65.943230"
+     transform="scale(0.73778,0.73778)"
+     style="font-size:18;font-weight:normal;stroke-width:1pt;font-family:Helvetica;"
+     id="text183">
+    <tspan
+       x="302.277954"
+       y="65.943184"
+       id="tspan360">
+Application</tspan>
+  </text>
+  <text
+     x="36.235924"
+     y="63.796055"
+     transform="scale(0.73778,0.73778)"
+     style="font-size:14;font-weight:normal;stroke-width:1pt;font-family:Helvetica;"
+     id="text188">
+    <tspan
+       x="36.235950"
+       y="63.796051"
+       id="tspan427">
+Transient Objects</tspan>
+  </text>
+  <text
+     x="180.416245"
+     y="290.543701"
+     transform="scale(0.73778,0.73778)"
+     style="font-size:18;font-weight:normal;stroke-width:1pt;font-family:Helvetica;"
+     id="text197">
+    <tspan
+       x="180.415939"
+       y="290.543549"
+       id="tspan421">
+Database</tspan>
+  </text>
+  <text
+     x="25.037701"
+     y="179.154755"
+     transform="scale(0.73778,0.73778)"
+     style="font-size:16;font-weight:normal;stroke-width:1pt;font-family:Helvetica;"
+     id="text216">
+    <tspan
+       x="25.037655"
+       y="179.154648"
+       id="tspan384">
+SessionFactory</tspan>
+  </text>
+  <g
+     transform="matrix(0.252763,0,0,0.765831,109.104,8.98517)"
+     style="font-size:12;"
+     id="g386">
+    <rect
+       width="285.502"
+       height="118.523"
+       x="16.6979"
+       y="99.2053"
+       style="fill:#757575;fill-rule:evenodd;stroke-width:1pt;"
+       id="rect387" />
+    <rect
+       width="285.502"
+       height="118.523"
+       x="13.4238"
+       y="95.9309"
+       style="fill:#d2d2d2;fill-rule:evenodd;stroke-width:1pt;"
+       id="rect388" />
+  </g>
+  <g
+     transform="matrix(0.297394,0,0,0.572692,101.502,21.6359)"
+     style="font-size:12;"
+     id="g364">
+    <rect
+       width="199.065"
+       height="61.5532"
+       x="61.8805"
+       y="68.4288"
+       style="fill:#757575;fill-rule:evenodd;stroke-width:1pt;"
+       id="rect365" />
+    <rect
+       width="199.065"
+       height="61.5532"
+       x="59.2613"
+       y="65.8095"
+       style="fill:#e0e0e0;fill-rule:evenodd;stroke-width:1pt;"
+       id="rect366" />
+  </g>
+  <text
+     x="202.746506"
+     y="102.992203"
+     transform="scale(0.73778,0.73778)"
+     style="font-size:14;font-weight:normal;stroke-width:1pt;font-family:Helvetica;text-anchor:middle;"
+     id="text367">
+    <tspan
+       x="202.746948"
+       y="102.992249"
+       id="tspan423">
+Persistent</tspan>
+    <tspan
+       x="202.746948"
+       y="116.992355"
+       id="tspan425">
+Objects</tspan>
+  </text>
+  <text
+     x="174.458496"
+     y="180.080795"
+     transform="scale(0.73778,0.73778)"
+     style="font-size:16;font-weight:normal;stroke-width:1pt;font-family:Helvetica;"
+     id="text389">
+    <tspan
+       x="174.458618"
+       y="180.080338"
+       id="tspan392">
+Session</tspan>
+  </text>
+  <g
+     transform="matrix(0.127369,0,0,0.765831,188.675,8.98517)"
+     style="font-size:12;"
+     id="g394">
+    <rect
+       width="285.502"
+       height="118.523"
+       x="16.6979"
+       y="99.2053"
+       style="fill:#757575;fill-rule:evenodd;stroke-width:1pt;"
+       id="rect395" />
+    <rect
+       width="285.502"
+       height="118.523"
+       x="13.4238"
+       y="95.9309"
+       style="fill:#d2d2d2;fill-rule:evenodd;stroke-width:1pt;"
+       id="rect396" />
+  </g>
+  <text
+     x="260.413269"
+     y="179.154739"
+     transform="scale(0.73778,0.73778)"
+     style="font-size:16;font-weight:normal;stroke-width:1pt;font-family:Helvetica;"
+     id="text397">
+    <tspan
+       x="260.412964"
+       y="179.154343"
+       id="tspan400">
+JDBC</tspan>
+  </text>
+  <g
+     transform="matrix(0.127369,0,0,0.765831,229.156,8.98517)"
+     style="font-size:12;"
+     id="g405">
+    <rect
+       width="285.502"
+       height="118.523"
+       x="16.6979"
+       y="99.2053"
+       style="fill:#757575;fill-rule:evenodd;stroke-width:1pt;"
+       id="rect406" />
+    <rect
+       width="285.502"
+       height="118.523"
+       x="13.4238"
+       y="95.9309"
+       style="fill:#d2d2d2;fill-rule:evenodd;stroke-width:1pt;"
+       id="rect407" />
+  </g>
+  <text
+     x="320.606903"
+     y="179.154739"
+     transform="scale(0.73778,0.73778)"
+     style="font-size:16;font-weight:normal;stroke-width:1pt;font-family:Helvetica;"
+     id="text408">
+    <tspan
+       x="320.606964"
+       y="179.154343"
+       id="tspan417">
+JNDI</tspan>
+  </text>
+  <g
+     transform="matrix(0.127369,0,0,0.765831,269.281,8.98517)"
+     style="font-size:12;"
+     id="g411">
+    <rect
+       width="285.502"
+       height="118.523"
+       x="16.6979"
+       y="99.2053"
+       style="fill:#757575;fill-rule:evenodd;stroke-width:1pt;"
+       id="rect412" />
+    <rect
+       width="285.502"
+       height="118.523"
+       x="13.4238"
+       y="95.9309"
+       style="fill:#d2d2d2;fill-rule:evenodd;stroke-width:1pt;"
+       id="rect413" />
+  </g>
+  <text
+     x="377.096313"
+     y="179.154739"
+     transform="scale(0.73778,0.73778)"
+     style="font-size:16;font-weight:normal;stroke-width:1pt;font-family:Helvetica;"
+     id="text414">
+    <tspan
+       x="377.096008"
+       y="179.154999"
+       id="tspan145">
+JTA</tspan>
+  </text>
+</svg>

Added: core/trunk/documentation/manual/fr-FR/src/main/docbook/images/overview.png
===================================================================
(Binary files differ)


Property changes on: core/trunk/documentation/manual/fr-FR/src/main/docbook/images/overview.png
___________________________________________________________________
Name: svn:mime-type
   + application/octet-stream

Added: core/trunk/documentation/manual/fr-FR/src/main/docbook/images/overview.svg
===================================================================
--- core/trunk/documentation/manual/fr-FR/src/main/docbook/images/overview.svg	                        (rev 0)
+++ core/trunk/documentation/manual/fr-FR/src/main/docbook/images/overview.svg	2007-10-09 18:28:36 UTC (rev 14074)
@@ -0,0 +1,250 @@
+<?xml version="1.0" standalone="no"?>
+<!DOCTYPE svg PUBLIC "-//W3C//DTD SVG 20010904//EN"
+"http://www.w3.org/TR/2001/REC-SVG-20010904/DTD/svg10.dtd"
+[
+ <!ATTLIST svg
+  xmlns:xlink CDATA #FIXED "http://www.w3.org/1999/xlink">
+]>
+<!-- Created with Sodipodi ("http://www.sodipodi.com/") -->
+<svg
+   xmlns="http://www.w3.org/2000/svg"
+   xmlns:xlink="http://www.w3.org/1999/xlink"
+   width="248.031"
+   height="248.031"
+   id="svg1">
+  <defs
+     id="defs3">
+    <linearGradient
+       x1="0"
+       y1="0"
+       x2="1"
+       y2="0"
+       id="linearGradient127"
+       gradientUnits="objectBoundingBox"
+       spreadMethod="pad">
+      <stop
+         style="stop-color:#000000;stop-opacity:1;"
+         offset="0"
+         id="stop128" />
+      <stop
+         style="stop-color:#ffffff;stop-opacity:1;"
+         offset="1"
+         id="stop129" />
+    </linearGradient>
+    <linearGradient
+       x1="0"
+       y1="0"
+       x2="1"
+       y2="0"
+       id="linearGradient130"
+       xlink:href="#linearGradient127"
+       gradientUnits="objectBoundingBox"
+       spreadMethod="pad" />
+    <radialGradient
+       cx="0.5"
+       cy="0.5"
+       fx="0.5"
+       fy="0.5"
+       r="0.5"
+       id="radialGradient131"
+       xlink:href="#linearGradient127"
+       gradientUnits="objectBoundingBox"
+       spreadMethod="pad" />
+  </defs>
+  <g
+     transform="matrix(0.771934,0,0,0.771934,4.36019,-3.02123)"
+     style="font-size:12;"
+     id="g158">
+    <rect
+       width="285.502"
+       height="77.2688"
+       x="16.6979"
+       y="17.3527"
+       style="fill:#757575;fill-rule:evenodd;stroke-width:1pt;"
+       id="rect136" />
+    <rect
+       width="285.502"
+       height="77.2688"
+       x="14.7335"
+       y="15.3883"
+       transform="translate(-1.30962,-1.30992)"
+       style="fill:#d2d2d2;fill-rule:evenodd;stroke-width:1pt;"
+       id="rect126" />
+  </g>
+  <g
+     transform="matrix(0.771934,0,0,0.771934,4.36019,3.04452)"
+     style="font-size:12;"
+     id="g161">
+    <rect
+       width="285.502"
+       height="118.523"
+       x="16.6979"
+       y="99.2053"
+       style="fill:#757575;fill-rule:evenodd;stroke-width:1pt;"
+       id="rect137" />
+    <rect
+       width="285.502"
+       height="118.523"
+       x="13.4238"
+       y="95.9309"
+       style="fill:#d2d2d2;fill-rule:evenodd;stroke-width:1pt;"
+       id="rect132" />
+  </g>
+  <g
+     transform="matrix(0.771934,0,0,0.771934,4.36019,8.0993)"
+     style="font-size:12;"
+     id="g164">
+    <rect
+       width="285.502"
+       height="77.2688"
+       x="16.6979"
+       y="222.966"
+       style="fill:#757575;fill-rule:evenodd;stroke-width:1pt;"
+       id="rect138" />
+    <rect
+       width="285.502"
+       height="77.2688"
+       x="14.7335"
+       y="221.002"
+       transform="translate(-1.30962,-1.30992)"
+       style="fill:#d2d2d2;fill-rule:evenodd;stroke-width:1pt;"
+       id="rect133" />
+  </g>
+  <g
+     transform="matrix(0.771934,0,0,0.543505,2.59104,21.1103)"
+     style="font-size:12;"
+     id="g167">
+    <rect
+       width="199.065"
+       height="61.5532"
+       x="61.8805"
+       y="68.4288"
+       style="fill:#757575;fill-rule:evenodd;stroke-width:1pt;"
+       id="rect134" />
+    <rect
+       width="199.065"
+       height="61.5532"
+       x="59.2613"
+       y="65.8095"
+       style="fill:#e0e0e0;fill-rule:evenodd;stroke-width:1pt;"
+       id="rect135" />
+  </g>
+  <text
+     x="105.392174"
+     y="56.568123"
+     transform="scale(0.771934,0.771934)"
+     style="font-size:24;font-weight:normal;stroke-width:1pt;font-family:Helvetica;"
+     id="text183">
+    <tspan
+       x="105.392273"
+       y="56.568146"
+       id="tspan186">
+Application</tspan>
+  </text>
+  <text
+     x="81.820183"
+     y="103.149330"
+     transform="scale(0.771934,0.771934)"
+     style="font-size:20;font-weight:normal;stroke-width:1pt;font-family:Helvetica;"
+     id="text188">
+    <tspan
+       x="81.820213"
+       y="103.149727"
+       id="tspan206">
+Persistent Objects</tspan>
+  </text>
+  <text
+     x="111.548180"
+     y="278.927887"
+     transform="scale(0.771934,0.771934)"
+     style="font-size:24;font-weight:normal;stroke-width:1pt;font-family:Helvetica;"
+     id="text197">
+    <tspan
+       x="111.547874"
+       y="278.927551"
+       id="tspan200">
+Database</tspan>
+  </text>
+  <text
+     x="94.436180"
+     y="153.805740"
+     transform="scale(0.771934,0.771934)"
+     style="font-size:24;font-weight:normal;stroke-width:1pt;font-family:Helvetica;"
+     id="text216">
+    <tspan
+       x="94.436180"
+       y="153.805740"
+       id="tspan221">
+HIBERNATE</tspan>
+  </text>
+  <g
+     transform="matrix(0.771934,0,0,0.771934,2.59083,1.02261)"
+     style="font-size:12;"
+     id="g254">
+    <g
+       transform="translate(4.58374,2.61928)"
+       id="g176">
+      <g
+         transform="matrix(0.571429,0,0,0.67347,-10.6174,117.093)"
+         id="g170">
+        <rect
+           width="199.065"
+           height="61.5532"
+           x="61.8805"
+           y="68.4288"
+           style="fill:#757575;fill-rule:evenodd;stroke-width:1pt;"
+           id="rect171" />
+        <rect
+           width="199.065"
+           height="61.5532"
+           x="59.2613"
+           y="65.8095"
+           style="fill:#e0e0e0;fill-rule:evenodd;stroke-width:1pt;"
+           id="rect172" />
+      </g>
+      <g
+         transform="matrix(0.571429,0,0,0.67347,138.682,117.093)"
+         id="g173">
+        <rect
+           width="199.065"
+           height="61.5532"
+           x="61.8805"
+           y="68.4288"
+           style="fill:#757575;fill-rule:evenodd;stroke-width:1pt;"
+           id="rect174" />
+        <rect
+           width="199.065"
+           height="61.5532"
+           x="59.2613"
+           y="65.8095"
+           style="fill:#e0e0e0;fill-rule:evenodd;stroke-width:1pt;"
+           id="rect175" />
+      </g>
+    </g>
+    <text
+       x="47.259438"
+       y="182.367538"
+       style="font-weight:bold;stroke-width:1pt;font-family:Courier;"
+       id="text191">
+      <tspan
+         x="47.259399"
+         y="182.367996"
+         id="tspan212">
+hibernate.</tspan>
+      <tspan
+         x="47.259399"
+         y="194.367996"
+         id="tspan214">
+properties</tspan>
+    </text>
+    <text
+       x="198.523010"
+       y="188.260941"
+       style="font-weight:normal;stroke-width:1pt;font-family:helvetica;"
+       id="text194">
+      <tspan
+         id="tspan195">
+XML Mapping</tspan>
+    </text>
+  </g>
+</svg>

Copied: core/trunk/documentation/manual/fr-FR/src/main/docbook/legal_notice.xml (from rev 14073, core/trunk/documentation/manual/en-US/src/main/docbook/legal_notice.xml)
===================================================================
--- core/trunk/documentation/manual/fr-FR/src/main/docbook/legal_notice.xml	                        (rev 0)
+++ core/trunk/documentation/manual/fr-FR/src/main/docbook/legal_notice.xml	2007-10-09 18:28:36 UTC (rev 14074)
@@ -0,0 +1,52 @@
+<?xml version='1.0'?>
+<!DOCTYPE legalnotice PUBLIC "-//OASIS//DTD DocBook XML V4.5//EN" "http://www.oasis-open.org/docbook/xml/4.5/docbookx.dtd">
+
+<!--
+  ~ Copyright (c) 2007, Red Hat Middleware, LLC. All rights reserved.
+  ~
+  ~ This copyrighted material is made available to anyone wishing to use, modify,
+  ~ copy, or redistribute it subject to the terms and conditions of the GNU
+  ~ Lesser General Public License, v. 2.1. This program is distributed in the
+  ~ hope that it will be useful, but WITHOUT A WARRANTY; without even the implied
+  ~ warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
+  ~ Lesser General Public License for more details. You should have received a
+  ~ copy of the GNU Lesser General Public License, v.2.1 along with this
+  ~ distribution; if not, write to the Free Software Foundation, Inc.,
+  ~ 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
+  ~
+  ~ Red Hat Author(s): Steve Ebersole
+  -->
+<legalnotice id="Legal_Notice">
+    <title>Legal Notice</title>
+    <para>
+        <address>
+            <street>1801 Varsity Drive</street>
+            <city>Raleigh</city>, <state>NC</state><postcode>27606-2072</postcode><country>USA</country>
+            <phone>Phone: +1 919 754 3700</phone>
+            <phone>Phone: 888 733 4281</phone>
+            <fax>Fax: +1 919 754 3701</fax>
+            <pob>PO Box 13588</pob><city>Research Triangle Park</city>, <state>NC</state><postcode>27709</postcode><country>USA</country>
+        </address>
+    </para>
+    <para>
+        Copyright <trademark class="copyright"></trademark> 2007 by Red Hat, Inc. This material may be distributed only subject to the terms and conditions set forth in the Open Publication License, V1.0 or later (the latest version is presently available at <ulink url="http://www.opencontent.org/openpub/">http://www.opencontent.org/openpub/</ulink>).
+    </para>
+    <para>
+        Distribution of substantively modified versions of this document is prohibited without the explicit permission of the copyright holder.
+    </para>
+    <para>
+        Distribution of the work or derivative of the work in any standard (paper) book form for commercial purposes is prohibited unless prior permission is obtained from the copyright holder.
+    </para>
+    <para>
+        Red Hat and the Red Hat "Shadow Man" logo are registered trademarks of Red Hat, Inc. in the United States and other countries.
+    </para>
+    <para>
+    All other trademarks referenced herein are the property of their respective owners.
+    </para>
+    <para>
+        The GPG fingerprint of the security at redhat.com key is:
+    </para>
+    <para>
+        CA 20 86 86 2B D6 9D FC 65 F6 EC C4 21 91 80 CD DB 42 A6 0E
+    </para>
+</legalnotice>
\ No newline at end of file

Deleted: core/trunk/documentation/manual/fr-FR/src/main/docbook/master.xml
===================================================================
--- core/trunk/documentation/manual/fr-FR/src/main/docbook/master.xml	2007-10-09 18:14:35 UTC (rev 14073)
+++ core/trunk/documentation/manual/fr-FR/src/main/docbook/master.xml	2007-10-09 18:28:36 UTC (rev 14074)
@@ -1,188 +0,0 @@
-<?xml version='1.0' encoding="iso-8859-1"?>
-<!DOCTYPE book PUBLIC "-//OASIS//DTD DocBook XML V4.3CR3//EN"
-                      "../support/docbook-dtd/docbookx.dtd"
-[
-<!ENTITY tutorial               SYSTEM "modules/tutorial.xml">
-<!ENTITY architecture           SYSTEM "modules/architecture.xml">
-<!ENTITY configuration          SYSTEM "modules/configuration.xml">
-<!ENTITY persistent-classes     SYSTEM "modules/persistent_classes.xml">
-<!ENTITY basic-mapping          SYSTEM "modules/basic_mapping.xml">
-<!ENTITY collection-mapping     SYSTEM "modules/collection_mapping.xml">
-<!ENTITY association-mapping    SYSTEM "modules/association_mapping.xml">
-<!ENTITY component-mapping      SYSTEM "modules/component_mapping.xml">
-<!ENTITY inheritance-mapping    SYSTEM "modules/inheritance_mapping.xml">
-<!ENTITY session-api            SYSTEM "modules/session_api.xml">
-<!ENTITY transactions           SYSTEM "modules/transactions.xml">
-<!ENTITY events                 SYSTEM "modules/events.xml">
-<!ENTITY batch                  SYSTEM "modules/batch.xml">
-<!ENTITY query-hql              SYSTEM "modules/query_hql.xml">
-<!ENTITY query-criteria         SYSTEM "modules/query_criteria.xml">
-<!ENTITY query-sql              SYSTEM "modules/query_sql.xml">
-<!ENTITY filters                SYSTEM "modules/filters.xml">
-<!ENTITY xml                    SYSTEM "modules/xml.xml">
-<!ENTITY performance            SYSTEM "modules/performance.xml">
-<!ENTITY toolset-guide          SYSTEM "modules/toolset_guide.xml">
-<!ENTITY example-parentchild    SYSTEM "modules/example_parentchild.xml">
-<!ENTITY example-weblog         SYSTEM "modules/example_weblog.xml">
-<!ENTITY example-mappings       SYSTEM "modules/example_mappings.xml">
-<!ENTITY best-practices         SYSTEM "modules/best_practices.xml">
-]>
-
-<book lang="fr">
-
-    <bookinfo>
-        <title>HIBERNATE - Persistance relationnelle en Java standard</title>
-        <subtitle>Documentation de référence d'Hibernate</subtitle>
-        <releaseinfo>3.3.0.beta1</releaseinfo>
-    </bookinfo>
-
-    <toc/>
-
-    <preface id="preface" revision="2">
-        <title>Préface</title>
-        <para>
-            Traducteur(s): Vincent Ricard, Sebastien Cesbron, Michael Courcy, Vincent Giguère, Baptiste Mathus, Emmanuel Bernard, Anthony Patricio
-        </para>
-        <para>
-            Travailler dans les deux univers que sont l'orienté objet et la base de données
-            relationnelle peut être lourd et consommateur en temps dans le monde de
-            l'entreprise d'aujourd'hui. Hibernate est un outil de  mapping objet/relationnel
-            pour le monde Java. Le terme mapping objet/relationnel (ORM) décrit la technique
-            consistant à faire le lien entre la représentation objet des données
-            et sa représentation relationnelle basée sur un schéma SQL.
-        </para>
-
-        <para>
-            Non seulement, Hibernate s'occupe du transfert des classes Java dans les tables
-            de la base de données (et des types de données Java dans les types de données SQL),
-            mais il permet de requêter les données et propose des moyens de les récupérer.
-            Il peut donc réduire de manière significative le temps de développement qui
-            aurait été autrement perdu dans une manipulation manuelle des données via SQL
-            et JDBC.
-        </para>
-
-        <para>
-            Le but d'Hibernate est de libérer le développeur de 95 pourcent des tâches de
-            programmation liées à la persistance des données communes. Hibernate n'est
-            probablement pas la meilleure solution pour les applications centrées sur les
-            données qui n'utilisent que les procédures stockées pour implémenter la logique
-            métier dans la base de données, il est le plus utile dans les modèles métier orientés
-            objets dont la logique métier est implémentée dans la couche Java dite intermédiaire.
-            Cependant, Hibernate vous aidera à supprimer ou à encapsuler le code SQL
-            spécifique à votre base de données et vous aidera sur la tâche commune qu'est
-            la transformation des données d'une représentation tabulaire à une
-            représentation sous forme de graphe d'objets.
-        </para>
-
-        <para>
-            Si vous êtes nouveau dans Hibernate et le mapping Objet/Relationnel voire même en Java,
-            suivez ces quelques étapes :
-        </para>
-
-        <orderedlist>
-            <listitem>
-                <para>
-                    Lisez <xref linkend="tutorial"/> pour un didacticiel plus long avec plus d'instructions étape par étape.
-                </para>
-            </listitem>
-            <listitem>
-                <para>
-                    Lisez <xref linkend="architecture"/> pour comprendre les environnements dans lesquels
-                    Hibernate peut être utilisé.
-                </para>
-            </listitem>
-            <listitem>
-                <para>
-                    Regardez le répertoire <literal>eg</literal> de la distribution Hibernate, il contient
-                    une application simple et autonome. Copiez votre pilote JDBC dans le répertoire
-                    <literal>lib/</literal> et éditez <literal>src/hibernate.properties</literal>, en
-                    positionnant correctement les valeurs pour votre base de données. A partir d'une
-                    invite de commande dans le répertoire de la distribution, tapez <literal>ant eg</literal>
-                    (cela utilise Ant), ou sous Windows tapez <literal>build eg</literal>.
-                </para>
-            </listitem>
-            <listitem>
-                <para>
-                    Faîtes de cette documentation de référence votre principale source d'information.
-                    Pensez à lire <emphasis>Java Persistence with Hibernate</emphasis>
-                    (http://www.manning.com/bauer2) si vous avez besoin de plus d'aide avec le design
-                    d'applications ou si vous préférez un tutoriel pas à pas. Visitez aussi
-                    http://caveatemptor.hibernate.org et téléchargez l'application exemple
-                    pour Java Persistence with Hibernate.
-                </para>
-            </listitem>
-            <listitem>
-                <para>
-                    Les questions les plus fréquemment posées (FAQs) trouvent leur réponse sur le
-                    site web Hibernate.
-                </para>
-            </listitem>
-            <listitem>
-                <para>
-                    Des démos, exemples et tutoriaux de tierces personnes sont référencés sur
-                    le site web Hibernate.
-                </para>
-            </listitem>
-            <listitem>
-                <para>
-                    La zone communautaire (Community Area) du site web Hibernate est une
-                    bonne source d'information sur les design patterns et sur différentes
-                    solutions d'intégration d'Hibernate (Tomcat, JBoss, Spring Framework, Struts,
-                    EJB, etc).
-                </para>
-            </listitem>
-         </orderedlist>
-
-         <para>
-             Si vous avez des questions, utilisez le forum utilisateurs du site web Hibernate.
-             Nous utilisons également l'outil de gestion des incidents JIRA pour tout ce qui
-             est rapports de bogue et demandes d'évolution. Si vous êtes intéressé par le
-             développement d'Hibernate, joignez-vous à la liste de diffusion de développement.
-         </para>
-
-         <para>
-             Le développement commercial, le support de production et les formations à Hibernate
-             sont proposés par JBoss Inc (voir http://www.hibernate.org/SupportTraining/). Hibernate
-             est un projet Open Source professionnel et un composant critique de la suite de produits
-             JBoss Enterprise Middleware System (JEMS).
-         </para>
-
-     </preface>
-
-    &tutorial;
-
-    &architecture;
-
-    &configuration;
-
-    &persistent-classes;
-
-    &basic-mapping;
-    &collection-mapping;
-    &association-mapping;
-    &component-mapping;
-    &inheritance-mapping;
-
-    &session-api;
-    &transactions;
-    &events;
-    &batch;
-
-    &query-hql;
-    &query-criteria;
-    &query-sql;
-    &filters;
-    &xml;
-
-    &performance;
-
-    &toolset-guide;
-
-    &example-parentchild;
-    &example-weblog;
-    &example-mappings;
-
-    &best-practices;
-
-</book>
-

Added: core/trunk/documentation/manual/fr-FR/src/main/docbook/translators.xml
===================================================================
--- core/trunk/documentation/manual/fr-FR/src/main/docbook/translators.xml	                        (rev 0)
+++ core/trunk/documentation/manual/fr-FR/src/main/docbook/translators.xml	2007-10-09 18:28:36 UTC (rev 14074)
@@ -0,0 +1,34 @@
+<?xml version='1.0'?>
+
+<!DOCTYPE authorgroup PUBLIC "-//OASIS//DTD DocBook XML V4.5//EN" "http://www.oasis-open.org/docbook/xml/4.5/docbookx.dtd">
+
+<authorgroup id="AuthorGroup">
+    <othercredit class="translator">
+        <firstname>Vincent</firstname>
+        <surname>Ricard</surname>
+    </othercredit>
+    <othercredit class="translator">
+        <firstname>Sebastien</firstname>
+        <surname>Cesbron</surname>
+    </othercredit>
+    <othercredit class="translator">
+        <firstname>Michael</firstname>
+        <surname>Courcy</surname>
+    </othercredit>
+    <othercredit class="translator">
+        <firstname>Vincent</firstname>
+        <surname>Giguère</surname>
+    </othercredit>
+    <othercredit class="translator">
+        <firstname>Baptiste</firstname>
+        <surname>Mathus</surname>
+    </othercredit>
+    <othercredit class="translator">
+        <firstname>Emmanuel</firstname>
+        <surname>Bernard</surname>
+    </othercredit>
+    <othercredit class="translator">
+        <firstname>Anthony</firstname>
+        <surname>Patricio</surname>
+    </othercredit>
+</authorgroup>
\ No newline at end of file




More information about the hibernate-commits mailing list