<?xml version="1.0" encoding="UTF-8"?>
<rss version="2.0"
	xmlns:content="http://purl.org/rss/1.0/modules/content/"
	xmlns:wfw="http://wellformedweb.org/CommentAPI/"
	xmlns:dc="http://purl.org/dc/elements/1.1/"
	xmlns:atom="http://www.w3.org/2005/Atom"
	xmlns:sy="http://purl.org/rss/1.0/modules/syndication/"
	xmlns:slash="http://purl.org/rss/1.0/modules/slash/"
	>

<channel>
	<title>Trux &#187; sérialisation</title>
	<atom:link href="http://trux.info/tag/serialisation/feed/" rel="self" type="application/rss+xml" />
	<link>http://trux.info</link>
	<description>Partage de mes astuces et découvertes</description>
	<lastBuildDate>Tue, 09 Jun 2009 19:47:29 +0000</lastBuildDate>
	<generator>http://wordpress.org/?v=2.8.2</generator>
	<language>en</language>
	<sy:updatePeriod>hourly</sy:updatePeriod>
	<sy:updateFrequency>1</sy:updateFrequency>
			<item>
		<title>Assurer la sérialisation d&#8217;un objet</title>
		<link>http://trux.info/2009/02/assurer-la-serialisation-dun-objet/</link>
		<comments>http://trux.info/2009/02/assurer-la-serialisation-dun-objet/#comments</comments>
		<pubDate>Sun, 08 Feb 2009 14:09:39 +0000</pubDate>
		<dc:creator>chris</dc:creator>
				<category><![CDATA[Informatique]]></category>
		<category><![CDATA[java]]></category>
		<category><![CDATA[sérialisation]]></category>
		<category><![CDATA[test]]></category>

		<guid isPermaLink="false">http://trux.info/?p=84</guid>
		<description><![CDATA[En java, n&#8217;importe quel objet implémentant l&#8217;interface Serializable peut être converti facilement en une séquence d&#8217;octets. Cette même séquence peut ensuite être reconverti en l&#8217;objet original. Ce mécanisme est par exemple utilisé pour transmettre des objets par RMI.
Voici une petite méthode pour vérifier que votre classe est bien sérialisable

import java.io.ByteArrayInputStream;
import java.io.ByteArrayOutputStream;
import java.io.IOException;
import java.io.ObjectInputStream;
import java.io.ObjectOutputStream;
import static [...]]]></description>
			<content:encoded><![CDATA[<p><img src="http://trux.info/wp-content/uploads/2009/02/conserve.jpg" alt="boîte de conserve" title="boîte de conserve" class="alignright size-full wp-image-83" />En java, n&#8217;importe quel objet implémentant l&#8217;interface <a href="http://java.sun.com/javase/6/docs/api/java/io/Serializable.html">Serializable</a> peut être converti facilement en une séquence d&#8217;octets. Cette même séquence peut ensuite être reconverti en l&#8217;objet original. Ce mécanisme est par exemple utilisé pour transmettre des objets par <a href="http://fr.wikipedia.org/wiki/Remote_method_invocation_(Java)">RMI</a>.</p>
<p>Voici une petite méthode pour vérifier que votre classe est bien sérialisable</p>

<div class="wp_syntax"><div class="code"><pre class="java java" style="font-family:monospace;"><span style="color: #000000; font-weight: bold;">import</span> <span style="color: #006699;">java.io.ByteArrayInputStream</span>;
<span style="color: #000000; font-weight: bold;">import</span> <span style="color: #006699;">java.io.ByteArrayOutputStream</span>;
<span style="color: #000000; font-weight: bold;">import</span> <span style="color: #006699;">java.io.IOException</span>;
<span style="color: #000000; font-weight: bold;">import</span> <span style="color: #006699;">java.io.ObjectInputStream</span>;
<span style="color: #000000; font-weight: bold;">import</span> <span style="color: #006699;">java.io.ObjectOutputStream</span>;
<span style="color: #000000; font-weight: bold;">import</span> <span style="color: #006699;">static</span> org.<span style="color: #006633;">junit</span>.<span style="color: #000000; font-weight: bold;">Assert</span>.<span style="color: #006633;">assertEquals</span>;
<span style="color: #000000; font-weight: bold;">import</span> <span style="color: #006699;">static</span> org.<span style="color: #006633;">junit</span>.<span style="color: #000000; font-weight: bold;">Assert</span>.<span style="color: #006633;">fail</span>;
&nbsp;
<span style="color: #000000; font-weight: bold;">public</span> <span style="color: #000000; font-weight: bold;">class</span> <span style="color: #000000; font-weight: bold;">Assert</span> <span style="color: #009900;">&#123;</span>
    <span style="color: #008000; font-style: italic; font-weight: bold;">/**
     * Assert that an object is serializable by dumping it and then reading it
     * back and finally by checking the original object and the dumped and read
     * object are equals.
     *
     * &lt;p&gt;Obviously, the method &lt;code&gt;equals()&lt;/code&gt; has to be implemented
     * correctly for this method can work.
     * @param objOriginal the instance which will be checked against serialization;
     * must implement &lt;code&gt;equals()&lt;/code&gt; or it won't work
     */</span>
    <span style="color: #000000; font-weight: bold;">public</span> <span style="color: #000000; font-weight: bold;">static</span> <span style="color: #000066; font-weight: bold;">void</span> assertSerializable<span style="color: #009900;">&#40;</span><span style="color: #003399;">Object</span> objOriginal<span style="color: #009900;">&#41;</span> <span style="color: #009900;">&#123;</span>
        <span style="color: #000000; font-weight: bold;">try</span> <span style="color: #009900;">&#123;</span>
            <span style="color: #000000; font-weight: bold;">final</span> <span style="color: #003399;">ByteArrayOutputStream</span> stream <span style="color: #339933;">=</span> <span style="color: #000000; font-weight: bold;">new</span> <span style="color: #003399;">ByteArrayOutputStream</span><span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span>;
            <span style="color: #000000; font-weight: bold;">final</span> <span style="color: #003399;">ObjectOutputStream</span> out <span style="color: #339933;">=</span> <span style="color: #000000; font-weight: bold;">new</span> <span style="color: #003399;">ObjectOutputStream</span><span style="color: #009900;">&#40;</span>stream<span style="color: #009900;">&#41;</span>;
            out.<span style="color: #006633;">writeObject</span><span style="color: #009900;">&#40;</span>objOriginal<span style="color: #009900;">&#41;</span>;
            out.<span style="color: #006633;">close</span><span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span>;
&nbsp;
            <span style="color: #000000; font-weight: bold;">final</span> <span style="color: #003399;">ObjectInputStream</span> in <span style="color: #339933;">=</span> <span style="color: #000000; font-weight: bold;">new</span> <span style="color: #003399;">ObjectInputStream</span><span style="color: #009900;">&#40;</span><span style="color: #000000; font-weight: bold;">new</span> <span style="color: #003399;">ByteArrayInputStream</span><span style="color: #009900;">&#40;</span>stream.<span style="color: #006633;">toByteArray</span><span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span><span style="color: #009900;">&#41;</span><span style="color: #009900;">&#41;</span>;
            <span style="color: #000000; font-weight: bold;">final</span> <span style="color: #003399;">Object</span> objSerialized <span style="color: #339933;">=</span> in.<span style="color: #006633;">readObject</span><span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span>;
            assertEquals<span style="color: #009900;">&#40;</span>objOriginal, objSerialized<span style="color: #009900;">&#41;</span>;
        <span style="color: #009900;">&#125;</span> <span style="color: #000000; font-weight: bold;">catch</span> <span style="color: #009900;">&#40;</span><span style="color: #003399;">IOException</span> e<span style="color: #009900;">&#41;</span> <span style="color: #009900;">&#123;</span>
            fail<span style="color: #009900;">&#40;</span><span style="color: #0000ff;">&quot;unable to serialize or deserialize object &quot;</span> <span style="color: #339933;">+</span> objOriginal <span style="color: #339933;">+</span> <span style="color: #0000ff;">&quot;: &quot;</span> <span style="color: #339933;">+</span> e.<span style="color: #006633;">getMessage</span><span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span><span style="color: #009900;">&#41;</span>;
        <span style="color: #009900;">&#125;</span> <span style="color: #000000; font-weight: bold;">catch</span> <span style="color: #009900;">&#40;</span><span style="color: #003399;">ClassNotFoundException</span> e<span style="color: #009900;">&#41;</span> <span style="color: #009900;">&#123;</span>
            <span style="color: #666666; font-style: italic;">// unlikely to happen...</span>
            fail<span style="color: #009900;">&#40;</span>e.<span style="color: #006633;">getMessage</span><span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span><span style="color: #009900;">&#41;</span>;
        <span style="color: #009900;">&#125;</span>
    <span style="color: #009900;">&#125;</span>
<span style="color: #009900;">&#125;</span></pre></div></div>

<p><span id="more-84"></span>Cette méthode sérialise une classe dans un buffer, puis relit ce buffer et s&#8217;assure que l&#8217;objet lu est bien égal à l&#8217;objet sérialisé.</p>
<p>Si ce test échoue, alors c&#8217;est que certaines données membres de l&#8217;objet testé ne sont pas sérialisables. Par exemple, un <a href="http://www.slf4j.org/apidocs/org/slf4j/Logger.html">Logger</a> ou un <a href="http://java.sun.com/javase/6/docs/api/java/lang/Thread.html">Thread</a> ne peuvent pas être sérialisés. Des données membres de ce type doivent donc être déclarés <code>transient</code> de la manière suivante</p>

<div class="wp_syntax"><div class="code"><pre class="java java" style="font-family:monospace;"><span style="color: #000000; font-weight: bold;">class</span> Foo <span style="color: #009900;">&#123;</span>
    <span style="color: #000000; font-weight: bold;">transient</span> <span style="color: #000000; font-weight: bold;">private</span> <span style="color: #003399;">Thread</span> thread;
    <span style="color: #000000; font-weight: bold;">transient</span> <span style="color: #000000; font-weight: bold;">private</span> Logger logger <span style="color: #339933;">=</span> LoggerFactory.<span style="color: #006633;">getLogger</span><span style="color: #009900;">&#40;</span><span style="color: #000000; font-weight: bold;">this</span>.<span style="color: #006633;">getClass</span><span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span><span style="color: #009900;">&#41;</span>;
    <span style="color: #000000; font-weight: bold;">private</span> <span style="color: #003399;">String</span> name;
&nbsp;
    <span style="color: #666666; font-style: italic;">// etc...</span>
<span style="color: #009900;">&#125;</span></pre></div></div>

<p>Attention une fois l&#8217;objet sérialisé puis désérialisé, les membres transients sont perdus. C&#8217;est ainsi qu&#8217;on se retrouve avec un logger à <code>null</code> et un <code>NullPointerException</code> assez rapidement&#8230; Dans ce cas, on peut implémenter une méthode privée ayant la signature <code>readObject(ObjectInputStream)</code> pour y restaurer le logger. La méthode doit être privée pour éviter tout appel par une autre classe ou toute surcharge par une classe fille.</p>

<div class="wp_syntax"><div class="code"><pre class="java java" style="font-family:monospace;">    <span style="color: #666666; font-style: italic;">// code...</span>
&nbsp;
    <span style="color: #000000; font-weight: bold;">private</span> <span style="color: #000066; font-weight: bold;">void</span> readObject<span style="color: #009900;">&#40;</span><span style="color: #003399;">ObjectInputStream</span> in<span style="color: #009900;">&#41;</span> <span style="color: #000000; font-weight: bold;">throws</span> <span style="color: #003399;">IOException</span>, <span style="color: #003399;">ClassNotFoundException</span> <span style="color: #009900;">&#123;</span>
        <span style="color: #666666; font-style: italic;">// default implementation</span>
        in.<span style="color: #006633;">defaultReadObject</span><span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span>;
        <span style="color: #666666; font-style: italic;">// restore our logger object</span>
        logger <span style="color: #339933;">=</span> LoggerFactory.<span style="color: #006633;">getLogger</span><span style="color: #009900;">&#40;</span><span style="color: #000000; font-weight: bold;">this</span>.<span style="color: #006633;">getClass</span><span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span><span style="color: #009900;">&#41;</span>;
    <span style="color: #009900;">&#125;</span>
&nbsp;
    <span style="color: #666666; font-style: italic;">// code...</span></pre></div></div>

<p>Tout les détails de la sérialisation sont expliqués <a href="http://java.sun.com/developer/technicalArticles/Programming/serialization/">sur le site de Sun</a>.</p>
]]></content:encoded>
			<wfw:commentRss>http://trux.info/2009/02/assurer-la-serialisation-dun-objet/feed/</wfw:commentRss>
		<slash:comments>0</slash:comments>
		</item>
	</channel>
</rss>

