<?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>Libre d'esprit &#187; performances</title> <atom:link href="http://libre-d-esprit.thinking-days.net/tag/performances/feed/" rel="self" type="application/rss+xml" /><link>http://libre-d-esprit.thinking-days.net</link> <description>Logiciels libres, joomla, talend, php, virtuemart, templates Joomla</description> <lastBuildDate>Thu, 28 Oct 2010 11:04:51 +0000</lastBuildDate> <language>en</language> <sy:updatePeriod>hourly</sy:updatePeriod> <sy:updateFrequency>1</sy:updateFrequency> <generator>http://wordpress.org/?v=3.0.4</generator> <item><title>Améliorer les performances de VirtueMart : Proposition d&#8217;une nouvelle table</title><link>http://libre-d-esprit.thinking-days.net/2009/01/ameliorer-les-performances-de-virtuemart-proposition-dune-nouvelle-table/</link> <comments>http://libre-d-esprit.thinking-days.net/2009/01/ameliorer-les-performances-de-virtuemart-proposition-dune-nouvelle-table/#comments</comments> <pubDate>Fri, 30 Jan 2009 17:48:41 +0000</pubDate> <dc:creator>Antoine</dc:creator> <category><![CDATA[Joomla]]></category> <category><![CDATA[VirtueMart]]></category> <category><![CDATA[performances]]></category> <guid
isPermaLink="false">http://libre-d-esprit.thinking-days.net/?p=42</guid> <description><![CDATA[Voici une proposition permettant d&#8217;améliorer le parcours de l&#8217;arborescence catégorie de VirtueMart, au détriment de la vitesse d&#8217;écriture. Ce billet fait directement suite à mon article &#171;&#160;Améliorer les performances de VirtueMart&#171;&#160;. Cette méthode nécessite de créer une nouvelle table que nous appellerons #__{vm}_category_tree, dont voici le schéma : category_id : identifiant de la catégorie category_path [...]]]></description> <content:encoded><![CDATA[<p>Voici une proposition permettant d&#8217;améliorer le parcours de l&#8217;arborescence catégorie de VirtueMart, au détriment de la vitesse d&#8217;écriture. Ce billet fait directement suite à mon article &laquo;&nbsp;<a
href="http://libre-d-esprit.thinking-days.net/2009/01/ameliorer-les-performance-de-virtuemart/" target="_self">Améliorer les performances de VirtueMart</a>&laquo;&nbsp;.</p><p>Cette méthode nécessite de créer une nouvelle table que nous appellerons #__{vm}_category_tree, dont voici le schéma :</p><ul><li>category_id : identifiant de la catégorie</li><li>category_path  : fil d&#8217;ariane de la catégorie sous forme d&#8217;un liste dénormalisée d&#8217;identifiant de catégorie séparée par &laquo;&nbsp;,&nbsp;&raquo;</li><li>level : niveau de profondeur de la catégorie étudiée</li></ul><p>Par exemple,  une catégorie ayant un  &laquo;&nbsp;fil d&#8217;ariane&nbsp;&raquo; ayant pour valeur &laquo;&nbsp;,1,6,184,&nbsp;&raquo; serait de niveau 4 (étant donné qu&#8217;il existe trois niveaux de catégories parentes).  Sa catégorie parente serait la catégorie &laquo;&nbsp;184&#8243;  qui aurait elle même comme parent &laquo;&nbsp;6&#8243; qui aurait elle même comme parent &laquo;&nbsp;1&#8243; qui n&#8217;aurait pas de catégorie parente.</p><p>Le choix du séparateur &laquo;&nbsp;,&nbsp;&raquo; permettra d&#8217;utiliser au besoin la colonne presque directement dans une requête SQL via le mot clé &laquo;&nbsp;in&nbsp;&raquo; si besoin.</p><p>Voici le SQL permettant de créer cette table :</p><div
class="codecolorer-container sql dawn" style="overflow:auto;white-space:nowrap;border:1px solid #9F9F9F;width:435px;"><div
class="sql codecolorer" style="padding:5px;font:normal 12px/1.4em Monaco, Lucida Console, monospace;white-space:nowrap"><span
style="color: #993333; font-weight: bold;">CREATE</span> <span
style="color: #993333; font-weight: bold;">TABLE</span> <span
style="color: #993333; font-weight: bold;">IF</span> <span
style="color: #993333; font-weight: bold;">NOT</span> <span
style="color: #993333; font-weight: bold;">EXISTS</span> <span
style="color: #ff0000;">`#__{vm}_category_tree`</span> <span
style="color: #66cc66;">&#40;</span><br
/> <span
style="color: #ff0000;">`category_id`</span> int<span
style="color: #66cc66;">&#40;</span><span
style="color: #cc66cc;">11</span><span
style="color: #66cc66;">&#41;</span> <span
style="color: #993333; font-weight: bold;">NOT</span> <span
style="color: #993333; font-weight: bold;">NULL</span><span
style="color: #66cc66;">,</span><br
/> <span
style="color: #ff0000;">`category_path`</span> varchar<span
style="color: #66cc66;">&#40;</span><span
style="color: #cc66cc;">255</span><span
style="color: #66cc66;">&#41;</span> <span
style="color: #993333; font-weight: bold;">NOT</span> <span
style="color: #993333; font-weight: bold;">NULL</span><span
style="color: #66cc66;">,</span><br
/> <span
style="color: #ff0000;">`level`</span> int<span
style="color: #66cc66;">&#40;</span><span
style="color: #cc66cc;">11</span><span
style="color: #66cc66;">&#41;</span> <span
style="color: #993333; font-weight: bold;">NOT</span> <span
style="color: #993333; font-weight: bold;">NULL</span><span
style="color: #66cc66;">,</span><br
/> <span
style="color: #993333; font-weight: bold;">KEY</span> <span
style="color: #ff0000;">`category_id`</span> <span
style="color: #66cc66;">&#40;</span><span
style="color: #ff0000;">`category_id`</span><span
style="color: #66cc66;">&#41;</span><span
style="color: #66cc66;">,</span><br
/> <span
style="color: #993333; font-weight: bold;">KEY</span> <span
style="color: #ff0000;">`category_path`</span> <span
style="color: #66cc66;">&#40;</span><span
style="color: #ff0000;">`category_path`</span><span
style="color: #66cc66;">&#41;</span><span
style="color: #66cc66;">,</span><br
/> <span
style="color: #993333; font-weight: bold;">KEY</span> <span
style="color: #ff0000;">`level`</span> <span
style="color: #66cc66;">&#40;</span><span
style="color: #ff0000;">`level`</span><span
style="color: #66cc66;">&#41;</span><br
/> <span
style="color: #66cc66;">&#41;</span> ENGINE<span
style="color: #66cc66;">=</span>MyISAM <span
style="color: #993333; font-weight: bold;">DEFAULT</span> CHARSET<span
style="color: #66cc66;">=</span>utf8;</div></div><p>Pour alimenter cette table, il faut d&#8217;abord executer une fois la requete suivante :</p><div
class="codecolorer-container sql dawn" style="overflow:auto;white-space:nowrap;border:1px solid #9F9F9F;width:435px;"><div
class="sql codecolorer" style="padding:5px;font:normal 12px/1.4em Monaco, Lucida Console, monospace;white-space:nowrap"><span
style="color: #993333; font-weight: bold;">INSERT</span> <span
style="color: #993333; font-weight: bold;">INTO</span><br
/> <span
style="color: #ff0000;">`#__{vm}_category_tree`</span><br
/> <span
style="color: #66cc66;">&#40;</span>category_id<span
style="color: #66cc66;">,</span>category_path<span
style="color: #66cc66;">,</span>level<span
style="color: #66cc66;">&#41;</span><br
/> <span
style="color: #993333; font-weight: bold;">SELECT</span><br
/> <span
style="color: #ff0000;">`#__{vm}_category.category_id`</span><span
style="color: #66cc66;">,</span><br
/> <span
style="color: #ff0000;">&quot;,&quot;</span><span
style="color: #66cc66;">,</span><br
/> <span
style="color: #cc66cc;">1</span><br
/> <span
style="color: #993333; font-weight: bold;">FROM</span><br
/> <span
style="color: #ff0000;">`#__{vm}_category`</span><br
/> <span
style="color: #993333; font-weight: bold;">INNER</span> <span
style="color: #993333; font-weight: bold;">JOIN</span><br
/> <span
style="color: #ff0000;">`#__{vm}_category_xref`</span><br
/> <span
style="color: #993333; font-weight: bold;">ON</span><br
/> <span
style="color: #ff0000;">`#__{vm}_category_xref`</span><span
style="color: #66cc66;">.</span>category_child_id<span
style="color: #66cc66;">=</span><span
style="color: #ff0000;">`#__{vm}_category`</span><span
style="color: #66cc66;">.</span>category_id<br
/> <span
style="color: #993333; font-weight: bold;">WHERE</span><br
/> <span
style="color: #ff0000;">`#__{vm}_category`</span><span
style="color: #66cc66;">.</span>category_publish<span
style="color: #66cc66;">=</span><span
style="color: #ff0000;">&quot;Y&quot;</span><br
/> <span
style="color: #993333; font-weight: bold;">AND</span><br
/> <span
style="color: #ff0000;">`#__{vm}_category_xref`</span><span
style="color: #66cc66;">.</span>category_parent_id<span
style="color: #66cc66;">=</span><span
style="color: #cc66cc;">0</span>;</div></div><p>Il faut ensuite exécuter pour chaque niveau :</p><div
class="codecolorer-container sql dawn" style="overflow:auto;white-space:nowrap;border:1px solid #9F9F9F;width:435px;"><div
class="sql codecolorer" style="padding:5px;font:normal 12px/1.4em Monaco, Lucida Console, monospace;white-space:nowrap"><span
style="color: #993333; font-weight: bold;">INSERT</span> <span
style="color: #993333; font-weight: bold;">INTO</span><br
/> <span
style="color: #ff0000;">`#__{vm}_category_tree`</span><br
/> <span
style="color: #66cc66;">&#40;</span>category_id<span
style="color: #66cc66;">,</span>category_path<span
style="color: #66cc66;">,</span>level<span
style="color: #66cc66;">&#41;</span><br
/> <span
style="color: #993333; font-weight: bold;">SELECT</span><br
/> <span
style="color: #ff0000;">`#__{vm}_category`</span><span
style="color: #66cc66;">.</span>category_id<span
style="color: #66cc66;">,</span><br
/> concat<span
style="color: #66cc66;">&#40;</span>IFNULL<span
style="color: #66cc66;">&#40;</span>parent_leaf<span
style="color: #66cc66;">.</span>category_path<span
style="color: #66cc66;">,</span><span
style="color: #ff0000;">&quot;&quot;</span><span
style="color: #66cc66;">&#41;</span><span
style="color: #66cc66;">,</span><span
style="color: #ff0000;">`#__{vm}_category_xref`</span><span
style="color: #66cc66;">.</span>category_parent_id<span
style="color: #66cc66;">,</span><span
style="color: #ff0000;">&quot;;&quot;</span><span
style="color: #66cc66;">&#41;</span><span
style="color: #66cc66;">,</span><br
/> IFNULL<span
style="color: #66cc66;">&#40;</span>parent_leaf<span
style="color: #66cc66;">.</span>level<span
style="color: #66cc66;">+</span><span
style="color: #cc66cc;">1</span><span
style="color: #66cc66;">,</span><span
style="color: #cc66cc;">0</span><span
style="color: #66cc66;">&#41;</span><br
/> <span
style="color: #993333; font-weight: bold;">FROM</span><br
/> <span
style="color: #ff0000;">`#__{vm}_category`</span><br
/> <span
style="color: #993333; font-weight: bold;">INNER</span> <span
style="color: #993333; font-weight: bold;">JOIN</span><br
/> <span
style="color: #ff0000;">`#__{vm}_category_xref`</span><br
/> <span
style="color: #993333; font-weight: bold;">ON</span><br
/> <span
style="color: #ff0000;">`#__{vm}_category_xref`</span><span
style="color: #66cc66;">.</span>category_child_id<span
style="color: #66cc66;">=</span><span
style="color: #ff0000;">`#__{vm}_category`</span><span
style="color: #66cc66;">.</span>category_id<br
/> <span
style="color: #993333; font-weight: bold;">LEFT</span> <span
style="color: #993333; font-weight: bold;">OUTER</span> <span
style="color: #993333; font-weight: bold;">JOIN</span><br
/> <span
style="color: #ff0000;">`#__{vm}_category_tree`</span> parent_leaf<br
/> <span
style="color: #993333; font-weight: bold;">ON</span><br
/> parent_leaf<span
style="color: #66cc66;">.</span>category_id<span
style="color: #66cc66;">=</span><span
style="color: #ff0000;">`#__{vm}_category_xref`</span><span
style="color: #66cc66;">.</span>category_parent_id<br
/> <span
style="color: #993333; font-weight: bold;">WHERE</span><br
/> <span
style="color: #ff0000;">`#__{vm}_category`</span><span
style="color: #66cc66;">.</span>category_publish<span
style="color: #66cc66;">=</span><span
style="color: #ff0000;">&quot;Y&quot;</span><br
/> <span
style="color: #993333; font-weight: bold;">AND</span><br
/> <span
style="color: #ff0000;">`#__{vm}_category_xref`</span><span
style="color: #66cc66;">.</span>category_parent_id <span
style="color: #993333; font-weight: bold;">IN</span> <span
style="color: #66cc66;">&#40;</span><span
style="color: #993333; font-weight: bold;">SELECT</span><br
/> category_id <span
style="color: #993333; font-weight: bold;">FROM</span> <span
style="color: #ff0000;">`#__{vm}_category_tree`</span> <span
style="color: #993333; font-weight: bold;">WHERE</span> level<span
style="color: #66cc66;">=</span>?<span
style="color: #66cc66;">&#41;</span></div></div><p>Le remplissage &laquo;&nbsp;au fil de l&#8217;eau&nbsp;&raquo; de cette table, fera l&#8217;objet d&#8217;autres billets.</p><p>Maintenant pour connaître tous les enfants directs et indirects d&#8217;une catégorie (&laquo;&nbsp;5&#8243; par exemple), il suffit d&#8217;éxécuter la requête suivante:</p><div
class="codecolorer-container sql dawn" style="overflow:auto;white-space:nowrap;border:1px solid #9F9F9F;width:435px;"><div
class="sql codecolorer" style="padding:5px;font:normal 12px/1.4em Monaco, Lucida Console, monospace;white-space:nowrap"><span
style="color: #993333; font-weight: bold;">SELECT</span> category_id<span
style="color: #66cc66;">,</span> level<br
/> <br
/> <span
style="color: #993333; font-weight: bold;">FROM</span> <span
style="color: #ff0000;">`#__{vm}_category_tree`</span><br
/> <br
/> <span
style="color: #993333; font-weight: bold;">WHERE</span> category_path <span
style="color: #993333; font-weight: bold;">LIKE</span> <span
style="color: #ff0000;">',5,%'</span>;</div></div><p>Une sacré économie de requetes SQL. Le résultat peut-être placée en cache si cela est possible. Il est également possible de complexifier cette requête en y rajoutant par exemple une jointure avec la table #__{vm}_category.</p><p><strong>Si vous êtes intéressé par cette modification, merci d’appuyer ma demande sur<a
title="forum virtuemart" href="http://forum.virtuemart.net/index.php?topic=47713.0" target="_blank"> le forum</a>.</strong></p> ]]></content:encoded> <wfw:commentRss>http://libre-d-esprit.thinking-days.net/2009/01/ameliorer-les-performances-de-virtuemart-proposition-dune-nouvelle-table/feed/</wfw:commentRss> <slash:comments>2</slash:comments> </item> <item><title>Améliorer les performance de Virtuemart : Constat</title><link>http://libre-d-esprit.thinking-days.net/2009/01/ameliorer-les-performance-de-virtuemart/</link> <comments>http://libre-d-esprit.thinking-days.net/2009/01/ameliorer-les-performance-de-virtuemart/#comments</comments> <pubDate>Fri, 30 Jan 2009 12:55:19 +0000</pubDate> <dc:creator>Antoine</dc:creator> <category><![CDATA[Joomla]]></category> <category><![CDATA[VirtueMart]]></category> <category><![CDATA[performances]]></category> <guid
isPermaLink="false">http://libre-d-esprit.thinking-days.net/?p=6</guid> <description><![CDATA[Dans le cadre professionnel, il m&#8217;est arrivé à moi et à mes collèges de créer des boutiques en ligne, basées sur Joomla / VirtueMart, proposant plus de 15000 produits. Après avoir réalisé des modifications nous permettant de tenir un tel catalogue, nous avons voulu les proposer à la communauté via le forum officiel de VirtueMart. [...]]]></description> <content:encoded><![CDATA[<p>Dans le cadre professionnel, il m&#8217;est arrivé à moi et à mes collèges de créer des boutiques en ligne, basées sur Joomla / VirtueMart, proposant plus de 15000 produits.</p><p>Après avoir réalisé des modifications nous permettant de tenir un tel catalogue, nous avons voulu les proposer à la communauté via le forum officiel de VirtueMart. Malheureusement, étonnement, notre demande a été ignorée pendant plusieurs mois.</p><p>L&#8217;un des problèmes majeurs, était le nombre de requêtes SQL nécessaires aux parcours de l&#8217;arborescence VirtueMart.</p><p>L&#8217;arborescence produit est stocké dans la table #__vm_category_xref dont voici le schéma simplifié :</p><ul><li>category_parent_id : identifiant de la catégorie parent</li><li>category_child_id : identifiant de la catégorie enfant</li></ul><p>Imaginons que votre site soit découpé en catégories de la manière suivante :</p><ol><li>CMS<ol><li>Joomla<ol><li>Joomla 1.0</li><li>Joomla 1.5</li><li>Joomla 1.6</li></ol></li><li>Drupal</li><li>EZ Publish</li><li>Typo 3</li></ol></li><li>E-Commerce<ol><li>VirtueMart</li><li>Magento</li><li>OS Commerce</li></ol></li></ol><p>Ce découpage est bien en dessous de l&#8217;arborescence que nous avons à gérer pour nos sites e-commerce.</p><p>Pour récupérer, l&#8217;arborescence et l&#8217;afficher il nous faut d&#8217;abord récupérer les catégories sans enfants (&laquo;&nbsp;CMS&nbsp;&raquo; et &laquo;&nbsp;E-Commerce&nbsp;&raquo;). Pour chacune de ces catégories, il faut voir si ces dernières ont des enfants et les afficher. Cet algorithme continue de manière itérative&#8230;</p><p>On voit bien que le nombre de requêtes SQL nécessaire est exponentiel. Certes, il y a le cache, mais ce dernier n&#8217;est pas toujours utilisable (ie : en back office).</p><p>Pire, imaginons que la page affichant la catégorie &laquo;&nbsp;CMS&nbsp;&raquo; doivent afficher l&#8217;ensemble des produits contenus dans la catégorie &laquo;&nbsp;CMS&nbsp;&raquo; et dans ces enfants directs et indirects, le tout trié par prix.</p><p>Ce problème explique en partie la lourdeur de l&#8217;arborescence du back-office par défaut de VirtueMart , lorsque le catalogue produit est volumineux.</p><p>J&#8217;expliquerais en détail la méthode que nous souhaitons soumettre à la communauté dans un prochain billet.</p> ]]></content:encoded> <wfw:commentRss>http://libre-d-esprit.thinking-days.net/2009/01/ameliorer-les-performance-de-virtuemart/feed/</wfw:commentRss> <slash:comments>1</slash:comments> </item> </channel> </rss>
