<?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>Data-Diggers.com &#187; Performance</title>
	<atom:link href="http://www.data-diggers.com/index.php/tag/performance/feed/" rel="self" type="application/rss+xml" />
	<link>http://www.data-diggers.com</link>
	<description>Zen Cart Optimization, Performance and A/B Split Testing Modules for Zen Cart</description>
	<lastBuildDate>Mon, 24 May 2010 18:56:27 +0000</lastBuildDate>
	<generator>http://wordpress.org/?v=2.9.2</generator>
	<language>en</language>
	<sy:updatePeriod>hourly</sy:updatePeriod>
	<sy:updateFrequency>1</sy:updateFrequency>
			<item>
		<title>Speed up admin/orders.php page</title>
		<link>http://www.data-diggers.com/index.php/2009/06/speed-up-adminorders-php-page/</link>
		<comments>http://www.data-diggers.com/index.php/2009/06/speed-up-adminorders-php-page/#comments</comments>
		<pubDate>Mon, 29 Jun 2009 05:38:47 +0000</pubDate>
		<dc:creator>admin</dc:creator>
				<category><![CDATA[Performance]]></category>
		<category><![CDATA[index]]></category>
		<category><![CDATA[Optimization]]></category>
		<category><![CDATA[sql]]></category>
		<category><![CDATA[Zen Cart]]></category>

		<guid isPermaLink="false">http://www.data-diggers.eu/?p=62</guid>
		<description><![CDATA[
			
				
			
		
There&#8217;s suboptimal query in admin/orders.php page which retrieves information about last orders. Unfortunately query is constructed in such way that MySQL scans whole orders, orders_products and orders_total table. As always it&#8217;s not a problem until orders table gets big ( for example 50 000 entries ). If You happen to have at least 10 000 [...]]]></description>
			<content:encoded><![CDATA[<div class="tweetmeme_button" style="float: right; margin-left: 10px;">
			<a href="http://api.tweetmeme.com/share?url=http%3A%2F%2Fwww.data-diggers.com%2Findex.php%2F2009%2F06%2Fspeed-up-adminorders-php-page%2F"><br />
				<img src="http://api.tweetmeme.com/imagebutton.gif?url=http%3A%2F%2Fwww.data-diggers.com%2Findex.php%2F2009%2F06%2Fspeed-up-adminorders-php-page%2F&amp;style=normal" height="61" width="50" /><br />
			</a>
		</div>
<p style="text-align: justify;">There&#8217;s suboptimal query in admin/orders.php page which retrieves information about last orders. Unfortunately query is constructed in such way that MySQL scans whole orders, orders_products and orders_total table. As always it&#8217;s not a problem until orders table gets big ( for example 50 000 entries ). If You happen to have at least 10 000 orders ( I wish You that <img src='http://www.data-diggers.com/wp-includes/images/smilies/icon_wink.gif' alt=';)' class='wp-smiley' />  ), You probably get impatient each time You request admin/orders.php page.</p>
<p style="text-align: justify;">Good news is that there is quick fix. Just add index on (orders_id, class) on orders_total table to speed up the query. Here&#8217;s MySQL statement which does that for You:</p>
<div style="text-align: justify;">
<div class="codesnip-container" >
<div class="sql codesnip" style="font-family:monospace;"><span class="kw1">ALTER</span> <span class="kw1">TABLE</span> orders_total <span class="kw1">ADD</span> <span class="kw1">INDEX</span> idx_oid_class<span class="br0">&#40;</span>orders_id<span class="sy0">,</span> class<span class="br0">&#41;</span></div>
</div>
</div>
<p style="text-align: justify;">The query is still suboptimal, but at least its quite fast until orders table gets really big (500 000 orders? It&#8217;ll depend on Your server).</p>
]]></content:encoded>
			<wfw:commentRss>http://www.data-diggers.com/index.php/2009/06/speed-up-adminorders-php-page/feed/</wfw:commentRss>
		<slash:comments>0</slash:comments>
		</item>
		<item>
		<title>Performance issues with Store Credit Module in admin area</title>
		<link>http://www.data-diggers.com/index.php/2009/06/performance-issues-with-store-credit-module-in-admin-area/</link>
		<comments>http://www.data-diggers.com/index.php/2009/06/performance-issues-with-store-credit-module-in-admin-area/#comments</comments>
		<pubDate>Tue, 23 Jun 2009 13:34:05 +0000</pubDate>
		<dc:creator>admin</dc:creator>
				<category><![CDATA[Performance]]></category>
		<category><![CDATA[store credit]]></category>
		<category><![CDATA[Zen Cart]]></category>

		<guid isPermaLink="false">http://www.data-diggers.eu/?p=55</guid>
		<description><![CDATA[
			
				
			
		
Store Credit is great module, unfortunately it&#8217;s preety inefecient in some places. For example, on every page request of admin/store_credit.php whole customers table is read, and for each customer additional SELECT and UPDATE query is executed to calculate and update pending points, even if the customer does not have any pending points!
It&#8217;s not a big deal [...]]]></description>
			<content:encoded><![CDATA[<div class="tweetmeme_button" style="float: right; margin-left: 10px;">
			<a href="http://api.tweetmeme.com/share?url=http%3A%2F%2Fwww.data-diggers.com%2Findex.php%2F2009%2F06%2Fperformance-issues-with-store-credit-module-in-admin-area%2F"><br />
				<img src="http://api.tweetmeme.com/imagebutton.gif?url=http%3A%2F%2Fwww.data-diggers.com%2Findex.php%2F2009%2F06%2Fperformance-issues-with-store-credit-module-in-admin-area%2F&amp;style=normal" height="61" width="50" /><br />
			</a>
		</div>
<p style="text-align: justify;"><strong>Store Credit</strong> is great module, unfortunately it&#8217;s preety inefecient in some places. For example, on every page request of<em> admin/store_credit.php</em> whole customers table is read, and for each customer additional SELECT and UPDATE query is executed to calculate and update pending points, even if the customer does not have any pending points!</p>
<p style="text-align: justify;">It&#8217;s not a big deal when You have up to 1000 customers, but when there are more then 100 000 customers page loads in 30 seconds (store_credit.php executes over 2 x customer count,  or in this example over 200 000 queries on each request).</p>
<p style="text-align: justify;">To address that, change following code in admin/store_credit.php:</p>
<div style="text-align: justify;">
<div class="codesnip-container" >
<div class="php codesnip" style="font-family:monospace;"><span class="kw2">function</span> store_pending_rewards<span class="br0">&#40;</span><span class="br0">&#41;</span> <span class="br0">&#123;</span><br />
&nbsp; &nbsp; &nbsp; &nbsp; <span class="kw2">global</span> <span class="re0">$db</span><span class="sy0">;</span></p>
<p>&nbsp; &nbsp; &nbsp; &nbsp; <span class="re0">$customers</span> <span class="sy0">=</span> <span class="re0">$db</span><span class="sy0">-&gt;</span><span class="me1">Execute</span><span class="br0">&#40;</span><span class="st0">&quot;SELECT customers_id FROM &quot;</span> <span class="sy0">.</span> TABLE_CUSTOMERS <span class="sy0">.</span> <span class="st0">&quot; ORDER BY customers_id ASC&quot;</span><span class="br0">&#41;</span><span class="sy0">;</span><br />
&nbsp; &nbsp; &nbsp; &nbsp; <span class="kw1">while</span> <span class="br0">&#40;</span><span class="sy0">!</span><span class="re0">$customers</span><span class="sy0">-&gt;</span><span class="me1">EOF</span><span class="br0">&#41;</span> <span class="br0">&#123;</span><br />
&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; <span class="re0">$customers_id</span> <span class="sy0">=</span> <span class="re0">$customers</span><span class="sy0">-&gt;</span><span class="me1">fields</span><span class="br0">&#91;</span><span class="st_h">&#8216;customers_id&#8217;</span><span class="br0">&#93;</span><span class="sy0">;</span><br />
&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; <span class="re0">$pending_rewards</span> <span class="sy0">=</span> <span class="re0">$this</span><span class="sy0">-&gt;</span><span class="me1">get_pending_rewards</span><span class="br0">&#40;</span><span class="re0">$customers_id</span><span class="br0">&#41;</span><span class="sy0">;</span><br />
&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; <span class="re0">$db</span><span class="sy0">-&gt;</span><span class="me1">Execute</span><span class="br0">&#40;</span><span class="st0">&quot;UPDATE &quot;</span> <span class="sy0">.</span> TABLE_STORE_CREDIT <span class="sy0">.</span> <span class="st0">&quot;<br />
&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; SET pending = &quot;</span> <span class="sy0">.</span> <span class="re0">$pending_rewards</span> <span class="sy0">.</span> <span class="st0">&quot;<br />
&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; WHERE customers_id = &quot;</span> <span class="sy0">.</span> <span class="re0">$customers_id</span> <span class="sy0">.</span> <span class="st0">&quot;<br />
&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; LIMIT 1&quot;</span><span class="br0">&#41;</span><span class="sy0">;</span><br />
&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; <span class="re0">$customers</span><span class="sy0">-&gt;</span><span class="me1">MoveNext</span><span class="br0">&#40;</span><span class="br0">&#41;</span><span class="sy0">;</span><br />
&nbsp; &nbsp; &nbsp; &nbsp; <span class="br0">&#125;</span><br />
<span class="br0">&#125;</span></div>
</div>
</div>
<p style="text-align: justify;">to:</p>
<div style="text-align: justify;">
<div class="codesnip-container" >
<div class="php codesnip" style="font-family:monospace;"><span class="kw2">function</span> store_pending_rewards<span class="br0">&#40;</span><span class="br0">&#41;</span> <span class="br0">&#123;</span><br />
&nbsp; &nbsp; &nbsp; &nbsp; <span class="kw2">global</span> <span class="re0">$db</span><span class="sy0">;</span></p>
<p>&nbsp; &nbsp; &nbsp; &nbsp; <span class="re0">$customers</span> <span class="sy0">=</span> <span class="re0">$db</span><span class="sy0">-&gt;</span><span class="me1">Execute</span><span class="br0">&#40;</span><span class="st0">&quot;SELECT DISTINCT customers_id FROM &quot;</span> <span class="sy0">.</span> TABLE_SC_REWARD_POINT_LOGS <span class="sy0">.</span> <span class="st0">&quot; ORDER BY customers_id ASC&quot;</span><span class="br0">&#41;</span><span class="sy0">;</span><br />
&nbsp; &nbsp; &nbsp; &nbsp; <span class="kw1">while</span> <span class="br0">&#40;</span><span class="sy0">!</span><span class="re0">$customers</span><span class="sy0">-&gt;</span><span class="me1">EOF</span><span class="br0">&#41;</span> <span class="br0">&#123;</span><br />
&nbsp; &nbsp; &nbsp; &nbsp; <span class="re0">$customers_id</span> <span class="sy0">=</span> <span class="re0">$customers</span><span class="sy0">-&gt;</span><span class="me1">fields</span><span class="br0">&#91;</span><span class="st_h">&#8216;customers_id&#8217;</span><span class="br0">&#93;</span><span class="sy0">;</span><br />
&nbsp; &nbsp; &nbsp; &nbsp; <span class="re0">$pending_rewards</span> <span class="sy0">=</span> <span class="re0">$this</span><span class="sy0">-&gt;</span><span class="me1">get_pending_rewards</span><span class="br0">&#40;</span><span class="re0">$customers_id</span><span class="br0">&#41;</span><span class="sy0">;</span><br />
&nbsp; &nbsp; &nbsp; &nbsp; <span class="kw1">if</span><span class="br0">&#40;</span><span class="re0">$pending_rewards</span> <span class="sy0">==</span> 0<span class="sy0">.</span>0<span class="br0">&#41;</span> <span class="br0">&#123;</span> <span class="re0">$customers</span><span class="sy0">-&gt;</span><span class="me1">MoveNext</span><span class="br0">&#40;</span><span class="br0">&#41;</span><span class="sy0">;</span> <span class="kw1">continue</span><span class="sy0">;</span> <span class="br0">&#125;</span><br />
&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; <span class="re0">$db</span><span class="sy0">-&gt;</span><span class="me1">Execute</span><span class="br0">&#40;</span><span class="st0">&quot;UPDATE &quot;</span> <span class="sy0">.</span> TABLE_STORE_CREDIT <span class="sy0">.</span> <span class="st0">&quot;<br />
&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; SET pending = &quot;</span> <span class="sy0">.</span> <span class="re0">$pending_rewards</span> <span class="sy0">.</span> <span class="st0">&quot;<br />
&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; WHERE customers_id = &quot;</span> <span class="sy0">.</span> <span class="re0">$customers_id</span> <span class="sy0">.</span> <span class="st0">&quot;<br />
&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; LIMIT 1&quot;</span><span class="br0">&#41;</span><span class="sy0">;</span><br />
&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; <span class="re0">$customers</span><span class="sy0">-&gt;</span><span class="me1">MoveNext</span><span class="br0">&#40;</span><span class="br0">&#41;</span><span class="sy0">;</span><br />
&nbsp; &nbsp; &nbsp; &nbsp; <span class="br0">&#125;</span><br />
<span class="br0">&#125;</span></div>
</div>
</div>
<p style="text-align: justify;">Thanks to that, only customers who actually have some pending points will be processed.</p>
]]></content:encoded>
			<wfw:commentRss>http://www.data-diggers.com/index.php/2009/06/performance-issues-with-store-credit-module-in-admin-area/feed/</wfw:commentRss>
		<slash:comments>0</slash:comments>
		</item>
		<item>
		<title>Query Log v1.5.1 released</title>
		<link>http://www.data-diggers.com/index.php/2009/06/query-log-v1-5-1-released/</link>
		<comments>http://www.data-diggers.com/index.php/2009/06/query-log-v1-5-1-released/#comments</comments>
		<pubDate>Tue, 23 Jun 2009 10:14:38 +0000</pubDate>
		<dc:creator>admin</dc:creator>
				<category><![CDATA[Performance]]></category>
		<category><![CDATA[Query Log]]></category>
		<category><![CDATA[Zen Cart]]></category>

		<guid isPermaLink="false">http://www.data-diggers.eu/?p=51</guid>
		<description><![CDATA[
			
				
			
		
Version v1.5.1 of Query Log is available. You can download it from: www.data-diggers.com/contribs/query-log/downloads/querylog-current.zip .
What&#8217;s new in this version:

You can now close &#8216;calculator&#8217; layer (it&#8217;s the tool that highlights queries that match given regular expression)
You can now disable query logging completely. In previous versions Query Log kept all queries in memory, no matter if You wanted to [...]]]></description>
			<content:encoded><![CDATA[<div class="tweetmeme_button" style="float: right; margin-left: 10px;">
			<a href="http://api.tweetmeme.com/share?url=http%3A%2F%2Fwww.data-diggers.com%2Findex.php%2F2009%2F06%2Fquery-log-v1-5-1-released%2F"><br />
				<img src="http://api.tweetmeme.com/imagebutton.gif?url=http%3A%2F%2Fwww.data-diggers.com%2Findex.php%2F2009%2F06%2Fquery-log-v1-5-1-released%2F&amp;style=normal" height="61" width="50" /><br />
			</a>
		</div>
<p style="text-align: justify;">Version v1.5.1 of<strong> Query Log </strong>is available. You can download it from: <a href="http://www.data-diggers.com/contribs/query-log/downloads/querylog-current.zip">www.data-diggers.com/contribs/query-log/downloads/querylog-current.zip</a> .</p>
<h2 style="text-align: justify;">What&#8217;s new in this version:</h2>
<ul style="text-align: justify;">
<li>You can now close &#8216;calculator&#8217; layer (it&#8217;s the tool that highlights queries that match given regular expression)</li>
<li>You can now disable query logging completely. In previous versions Query Log kept all queries in memory, no matter if You wanted to log them (display them) or not.</li>
</ul>
]]></content:encoded>
			<wfw:commentRss>http://www.data-diggers.com/index.php/2009/06/query-log-v1-5-1-released/feed/</wfw:commentRss>
		<slash:comments>0</slash:comments>
		</item>
		<item>
		<title>Speed up &#8216;Order history&#8217; query by 50%-75%</title>
		<link>http://www.data-diggers.com/index.php/2009/06/speed-up-order-history-query-by-50-75/</link>
		<comments>http://www.data-diggers.com/index.php/2009/06/speed-up-order-history-query-by-50-75/#comments</comments>
		<pubDate>Mon, 22 Jun 2009 14:46:58 +0000</pubDate>
		<dc:creator>admin</dc:creator>
				<category><![CDATA[Performance]]></category>
		<category><![CDATA[index]]></category>
		<category><![CDATA[Optimization]]></category>
		<category><![CDATA[sql]]></category>
		<category><![CDATA[Zen Cart]]></category>

		<guid isPermaLink="false">http://www.data-diggers.eu/?p=49</guid>
		<description><![CDATA[
			
				
			
		
I noticed that following query takes long time to execute:


SELECT DISTINCT op.products_id
FROM orders o, orders_products op, products p
WHERE o.customers_id = &#8216;2345&#8242;
AND o.orders_id = op.orders_id
AND op.products_id = p.products_id
AND p.products_status = &#8216;1&#8242;
GROUP BY products_id
ORDER BY o.date_purchased DESC
LIMIT 6


I noticed that there&#8217;s no index on orders table on customers_id field. Without it MySQL has to scan whole table [...]]]></description>
			<content:encoded><![CDATA[<div class="tweetmeme_button" style="float: right; margin-left: 10px;">
			<a href="http://api.tweetmeme.com/share?url=http%3A%2F%2Fwww.data-diggers.com%2Findex.php%2F2009%2F06%2Fspeed-up-order-history-query-by-50-75%2F"><br />
				<img src="http://api.tweetmeme.com/imagebutton.gif?url=http%3A%2F%2Fwww.data-diggers.com%2Findex.php%2F2009%2F06%2Fspeed-up-order-history-query-by-50-75%2F&amp;style=normal" height="61" width="50" /><br />
			</a>
		</div>
<p style="text-align: justify;">I noticed that following query takes long time to execute:</p>
<div style="text-align: justify;">
<div class="codesnip-container" >
<div class="sql codesnip" style="font-family:monospace;"><span class="kw1">SELECT</span> <span class="kw1">DISTINCT</span> op<span class="sy0">.</span>products_id<br />
<span class="kw1">FROM</span> orders o<span class="sy0">,</span> orders_products op<span class="sy0">,</span> products p<br />
<span class="kw1">WHERE</span> o<span class="sy0">.</span>customers_id <span class="sy0">=</span> <span class="st0">&#8216;2345&#8242;</span><br />
<span class="kw1">AND</span> o<span class="sy0">.</span>orders_id <span class="sy0">=</span> op<span class="sy0">.</span>orders_id<br />
<span class="kw1">AND</span> op<span class="sy0">.</span>products_id <span class="sy0">=</span> p<span class="sy0">.</span>products_id<br />
<span class="kw1">AND</span> p<span class="sy0">.</span>products_status <span class="sy0">=</span> <span class="st0">&#8216;1&#8242;</span><br />
<span class="kw1">GROUP</span> <span class="kw1">BY</span> products_id<br />
<span class="kw1">ORDER</span> <span class="kw1">BY</span> o<span class="sy0">.</span>date_purchased <span class="kw1">DESC</span><br />
<span class="kw1">LIMIT</span> <span class="nu0">6</span></div>
</div>
</div>
<p style="text-align: justify;">I noticed that there&#8217;s no index on <strong>orders </strong>table on <strong><em>customers_id</em></strong> field. Without it MySQL has to scan whole table to find orders by <strong><em>customers_id</em></strong><em> </em>(in this case &#8216;2345&#8242;). If <strong>orders </strong>table is small there&#8217;s no problem, but when it has 10 000 or more entries it can noticably slow down Zen Cart. So, let&#8217;s add index on that table</p>
<div style="text-align: justify;">
<div class="codesnip-container" >
<div class="sql codesnip" style="font-family:monospace;"><span class="kw1">ALTER</span> <span class="kw1">TABLE</span> <span class="st0">`orders`</span> <span class="kw1">ADD</span> <span class="kw1">INDEX</span> <span class="st0">`idx_cid_datepurchased`</span><span class="br0">&#40;</span><span class="st0">`customers_id`</span><span class="sy0">,</span> <span class="st0">`date_purchased`</span><span class="br0">&#41;</span>;</div>
</div>
</div>
<p style="text-align: justify;">I included <strong><em>date_purchased</em></strong> in index, because some pages in admin area will use it for searching all orders of given customer.</p>
<p style="text-align: justify;">In my case it decreased query time from 0.3 sec to 0.08 sec. It&#8217;s still too much, but it&#8217;s better then nothing.</p>
]]></content:encoded>
			<wfw:commentRss>http://www.data-diggers.com/index.php/2009/06/speed-up-order-history-query-by-50-75/feed/</wfw:commentRss>
		<slash:comments>0</slash:comments>
		</item>
		<item>
		<title>Query Cache v1.5 released</title>
		<link>http://www.data-diggers.com/index.php/2009/01/query-cache-v1-5-released/</link>
		<comments>http://www.data-diggers.com/index.php/2009/01/query-cache-v1-5-released/#comments</comments>
		<pubDate>Mon, 12 Jan 2009 14:24:49 +0000</pubDate>
		<dc:creator>admin</dc:creator>
				<category><![CDATA[Performance]]></category>
		<category><![CDATA[Query Cache]]></category>
		<category><![CDATA[Zen Cart]]></category>

		<guid isPermaLink="false">http://www.data-diggers.eu/?p=37</guid>
		<description><![CDATA[
			
				
			
		
Version 1.5 of Query Cache for Zen Cart has been released. New version reduces query count by 80% (previous version reduced query count by &#8216;only&#8217; 50%). Here&#8217;s list of changes:

970 queries down to 198 queries ( v1.0 executed about 450 queries )
some performance improvements to code
includes/functions/functions_categories.php has been rewritten to use cache and prefetch data. [...]]]></description>
			<content:encoded><![CDATA[<div class="tweetmeme_button" style="float: right; margin-left: 10px;">
			<a href="http://api.tweetmeme.com/share?url=http%3A%2F%2Fwww.data-diggers.com%2Findex.php%2F2009%2F01%2Fquery-cache-v1-5-released%2F"><br />
				<img src="http://api.tweetmeme.com/imagebutton.gif?url=http%3A%2F%2Fwww.data-diggers.com%2Findex.php%2F2009%2F01%2Fquery-cache-v1-5-released%2F&amp;style=normal" height="61" width="50" /><br />
			</a>
		</div>
<p style="text-align: justify;">Version 1.5 of<strong> Query Cache</strong> for Zen Cart has been released. New version <strong>reduces query count by 80%</strong> (previous version reduced query count by &#8216;only&#8217; 50%). Here&#8217;s list of changes:</p>
<ul style="text-align: justify;">
<li>970 queries down to 198 queries ( v1.0 executed about 450 queries )</li>
<li>some performance improvements to code</li>
<li>includes/functions/functions_categories.php has been rewritten to use cache and prefetch data. It reduces query count by about 100 queries (it depends on number of categories in Your store)</li>
<li>basic queries for product from products table (for example &#8220;<em>select products_name, manufacturers_id from products where products_id = &#8216;7&#8242;</em>&#8220;) can now be rewritten to &#8220;<em>select * from products where products_id = &#8216;7&#8242;</em>&#8220;. It saves about 100 queries on default Zen Cart demo store.<strong><br />
</strong></li>
</ul>
<p style="text-align: justify;">Download <a href="http://www.data-diggers.com/contribs/query-cache/downloads/querycache-current.zip">Query Cache v1.5</a>. See <a href="http://www.data-diggers.eu/index.php/2008/12/query-cache-for-zen-cart-released/">updated blog entry on Query Cache</a> for updated charts, demo stores and screencast.</p>
<h2 style="text-align: justify;"><strong>Stay in touch<br />
</strong></h2>
<p style="text-align: justify;">Just type Your address here to be notified of new versions of Query Cache (You&#8217;ll receive only updates on Query Cache). Quick info: We hate spam, Your email will not be given to anyone.</p>
]]></content:encoded>
			<wfw:commentRss>http://www.data-diggers.com/index.php/2009/01/query-cache-v1-5-released/feed/</wfw:commentRss>
		<slash:comments>0</slash:comments>
		</item>
		<item>
		<title>InnoDB vs MyISAM performance in Zen Cart. Which is better?</title>
		<link>http://www.data-diggers.com/index.php/2009/01/innodb-vs-myisam-performance-in-zen-cart-which-is-better/</link>
		<comments>http://www.data-diggers.com/index.php/2009/01/innodb-vs-myisam-performance-in-zen-cart-which-is-better/#comments</comments>
		<pubDate>Tue, 06 Jan 2009 13:36:31 +0000</pubDate>
		<dc:creator>admin</dc:creator>
				<category><![CDATA[Performance]]></category>
		<category><![CDATA[innodb vs myisam]]></category>
		<category><![CDATA[Zen Cart]]></category>

		<guid isPermaLink="false">http://www.data-diggers.eu/?p=31</guid>
		<description><![CDATA[
			
				
			
		
Zen Cart uses MyISAM tables to store data, but MySQL offers other storage engines too. Is MyISAM the best choice? Is it the fastest one? These questions will be answered.. right now: No, it isn&#8217;t (at least not always). Read below to find out more.
Performance test
Note: In test We used MySQL 5.0.41. Results can vary depending [...]]]></description>
			<content:encoded><![CDATA[<div class="tweetmeme_button" style="float: right; margin-left: 10px;">
			<a href="http://api.tweetmeme.com/share?url=http%3A%2F%2Fwww.data-diggers.com%2Findex.php%2F2009%2F01%2Finnodb-vs-myisam-performance-in-zen-cart-which-is-better%2F"><br />
				<img src="http://api.tweetmeme.com/imagebutton.gif?url=http%3A%2F%2Fwww.data-diggers.com%2Findex.php%2F2009%2F01%2Finnodb-vs-myisam-performance-in-zen-cart-which-is-better%2F&amp;style=normal" height="61" width="50" /><br />
			</a>
		</div>
<p style="text-align: justify;">Zen Cart uses MyISAM tables to store data, but MySQL offers other storage engines too. Is MyISAM the best choice? Is it the fastest one? These questions will be answered.. right now: No, it isn&#8217;t (at least not always). Read below to find out more.</p>
<h2 style="text-align: justify;"><strong>Performance test</strong></h2>
<p style="text-align: justify;"><strong>Note</strong>: <em>In test We used MySQL 5.0.41. Results can vary depending on MySQL version You use.</em></p>
<p style="text-align: justify;">Let&#8217;s find out which of the two is faster. To do this We&#8217;ll need to test their performance. We created Java application which executes typical SELECT queries against Zen Cart demo store database and measures query performance. Here are some of those queries:</p>
<p style="text-align: justify;">SELECT queries</p>
<div style="text-align: justify;">
<div class="codesnip-container" >
<div class="sql codesnip" style="font-family:monospace;"><span class="kw1">SELECT</span> SQL_NO_CACHE count<span class="br0">&#40;</span><span class="sy0">*</span><span class="br0">&#41;</span> <span class="kw1">AS</span> total<br />
<span class="kw1">FROM</span> products p<span class="sy0">,</span> products_to_categories p2c<br />
<span class="kw1">WHERE</span> p<span class="sy0">.</span>products_id <span class="sy0">=</span> p2c<span class="sy0">.</span>products_id<br />
<span class="kw1">AND</span> p<span class="sy0">.</span>products_status <span class="sy0">=</span> <span class="st0">&#8216;1&#8242;</span><br />
<span class="kw1">AND</span> p2c<span class="sy0">.</span>categories_id <span class="sy0">=</span> <span class="st0">&#8216;22&#8242;</span></div>
</div>
</div>
<div style="text-align: justify;">
<div class="codesnip-container" >
<div class="sql codesnip" style="font-family:monospace;"><span class="kw1">SELECT</span> SQL_NO_CACHE products_type<br />
<span class="kw1">FROM</span> products<br />
<span class="kw1">WHERE</span> products_id <span class="sy0">=</span> <span class="st0">&#8216;12&#8242;</span></div>
</div>
</div>
<div style="text-align: justify;">
<div class="codesnip-container" >
<div class="sql codesnip" style="font-family:monospace;"><span class="kw1">SELECT</span> SQL_NO_CACHE <span class="kw1">DISTINCT</span> p<span class="sy0">.</span>products_id<span class="sy0">,</span> p<span class="sy0">.</span>products_image<span class="sy0">,</span> pd<span class="sy0">.</span>products_name<span class="sy0">,</span> p<span class="sy0">.</span>master_categories_id<br />
<span class="kw1">FROM</span> <span class="br0">&#40;</span>products p<br />
<span class="kw1">LEFT</span> <span class="kw1">JOIN</span> featured f <span class="kw1">ON</span> p<span class="sy0">.</span>products_id <span class="sy0">=</span> f<span class="sy0">.</span>products_id<br />
<span class="kw1">LEFT</span> <span class="kw1">JOIN</span> products_description pd <span class="kw1">ON</span> p<span class="sy0">.</span>products_id <span class="sy0">=</span> pd<span class="sy0">.</span>products_id <span class="br0">&#41;</span><br />
<span class="kw1">WHERE</span> p<span class="sy0">.</span>products_id <span class="sy0">=</span> f<span class="sy0">.</span>products_id<br />
<span class="kw1">AND</span> p<span class="sy0">.</span>products_id <span class="sy0">=</span> pd<span class="sy0">.</span>products_id<br />
<span class="kw1">AND</span> p<span class="sy0">.</span>products_status <span class="sy0">=</span> 1 <span class="kw1">AND</span> f<span class="sy0">.</span><span class="kw1">STATUS</span> <span class="sy0">=</span> 1<br />
<span class="kw1">AND</span> pd<span class="sy0">.</span>language_id <span class="sy0">=</span> <span class="st0">&#8216;1&#8242;</span></div>
</div>
</div>
<p style="text-align: justify;">Note that We added <strong>SQL_NO_CACHE</strong> to prevent MySQL from caching query results.</p>
<p style="text-align: justify;">Now, it&#8217;s important to simulate many customers wandering around Zen Cart store. Therefore We used 10 threads to send queries to database.</p>
<p style="text-align: justify;">InnoDB managed to perform <strong>1186 </strong>queries per second on average, where MyISAM executed only <strong>958 </strong>queries per second on average. <strong>InnoDB was faster by almost 25%!</strong></p>
<h2 style="text-align: justify;"><strong>Locking strategy</strong></h2>
<p style="text-align: justify;">Very important feature (from performance perspective) is that InnoDB uses per row locking, where MyISAM uses table locking. What does it mean? We&#8217;ll clarify it with example.</p>
<p style="text-align: justify;">Let&#8217;s assume that We&#8217;re executing following update against products table:</p>
<div style="text-align: justify;">
<div class="codesnip-container" >
<div class="sql codesnip" style="font-family:monospace;"><span class="kw1">UPDATE</span> products<br />
<span class="kw1">SET</span> products_ordered <span class="sy0">=</span> products_ordered <span class="sy0">+</span> 1<br />
<span class="kw1">WHERE</span> products_id <span class="sy0">=</span> <span class="nu0">12</span></div>
</div>
</div>
<p style="text-align: justify;">and other thread (other http request from other customer) is executing at the same time following query:</p>
<div style="text-align: justify;">
<div class="codesnip-container" >
<div class="sql codesnip" style="font-family:monospace;"><span class="kw1">SELECT</span> products_type<br />
<span class="kw1">FROM</span> products<br />
<span class="kw1">WHERE</span> products_id <span class="sy0">=</span> <span class="st0">&#8216;17&#8242;</span></div>
</div>
</div>
<p style="text-align: justify;">Because MyISAM uses table locking when updates are made to tables, it will prevent execution of other SELECT queries until update statement finishes, even if those queries don&#8217;t look at updated rows.</p>
<p style="text-align: justify;">InnoDB on the other hand will lock only row with products_id field set to 17, allowing concurrent execution of SELECT queries (unless those queries are asking for data from updated row).</p>
<p style="text-align: justify;">It does not give much performance boost when Your store has low traffic, but when it&#8217;ll get more popular (hopefully<img src="http://www.data-diggers.com/sites/all/modules/fckeditor/fckeditor/editor/images/smiley/msn/wink_smile.gif" alt="" />) and You&#8217;ll have ten thousands visits per day it&#8217;ll make a difference ( the more traffic You&#8217;ll get the bigger the difference should be).</p>
<h2 style="text-align: justify;"><strong>How to convert MyISAM table to InnoDB table</strong></h2>
<p style="text-align: justify;">To convert any table example to InnoDB execute following SQL code:</p>
<div style="text-align: justify;">
<div class="codesnip-container" >
<div class="sql codesnip" style="font-family:monospace;"><span class="kw1">ALTER</span> <span class="kw1">TABLE</span> example ENGINE <span class="sy0">=</span> InnoDB</div>
</div>
</div>
<p style="text-align: justify;">Unfortunately Zen Cart database contains about 80 tables, so changing each of them by hand would be inconvenient. Also, one may want to change back to MyISAM for some reason, and it would have to repeat whole process again. To address that problem We created simple Zen Cart contribution that automates conversion from MyISAM to InnoDB. You can download it here:</p>
<p style="text-align: center;"><a href="http://www.data-diggers.com/contribs/change-storage-engine/downloads/change_storage_engine_current.zip">Download Change Storage Engine</a></p>
<p style="text-align: justify;">Installation is very easy, just copy unzipped folder to Your store directory. This contribution does not overwrite any Zen Cart files, so You don&#8217;t have to worry about that. To change <strong>all</strong> tables in Your database from MyISAM/InnoDB to InnoDB/MyISAM go to <em>Tools-&gt;Change Storage Engine</em> and click &#8216;Change&#8217;. That&#8217;s it!</p>
<h2 style="text-align: justify;"><strong>Summary</strong></h2>
<p style="text-align: justify;">InnoDB is faster then MyISAM engine, it also scales better. But before You change all Your tables to InnoDB make sure to (as always) make backup of Your database. Also, after changing tables to InnoDB check if Your store runs faster as MySQL performance differs from version to version.</p>
<h2 style="text-align: justify;"><strong>Updates</strong></h2>
<p style="text-align: justify;">Version 1.1 of Change Storage Engine is available (use link above, it always points to newest version). It&#8217;ll omit MyISAM tables with FULLTEXT indexes (InnoDB does not support FULLTEXT indexes).</p>
]]></content:encoded>
			<wfw:commentRss>http://www.data-diggers.com/index.php/2009/01/innodb-vs-myisam-performance-in-zen-cart-which-is-better/feed/</wfw:commentRss>
		<slash:comments>1</slash:comments>
		</item>
		<item>
		<title>Query Log Released</title>
		<link>http://www.data-diggers.com/index.php/2008/12/query-log-released/</link>
		<comments>http://www.data-diggers.com/index.php/2008/12/query-log-released/#comments</comments>
		<pubDate>Thu, 18 Dec 2008 12:12:08 +0000</pubDate>
		<dc:creator>admin</dc:creator>
				<category><![CDATA[Performance]]></category>
		<category><![CDATA[Query Log]]></category>
		<category><![CDATA[screencast]]></category>
		<category><![CDATA[Zen Cart]]></category>

		<guid isPermaLink="false">http://www.data-diggers.eu/?p=21</guid>
		<description><![CDATA[
			
				
			
		
Query Log for Zen Cart is open source, simple tool for monitoring performance of SQL queries. Depending on configuration it will display or save all executed queries sent to database together with information how much time each query took and which page and session executed it. With Query Log and some SQL knowledge You can [...]]]></description>
			<content:encoded><![CDATA[<div class="tweetmeme_button" style="float: right; margin-left: 10px;">
			<a href="http://api.tweetmeme.com/share?url=http%3A%2F%2Fwww.data-diggers.com%2Findex.php%2F2008%2F12%2Fquery-log-released%2F"><br />
				<img src="http://api.tweetmeme.com/imagebutton.gif?url=http%3A%2F%2Fwww.data-diggers.com%2Findex.php%2F2008%2F12%2Fquery-log-released%2F&amp;style=normal" height="61" width="50" /><br />
			</a>
		</div>
<p style="text-align: justify;"><strong>Query Log for Zen Cart</strong> is open source, simple tool for monitoring performance of SQL queries. Depending on configuration it will display or save all executed queries sent to database together with information how much time each query took and which page and session executed it. With Query Log and some SQL knowledge You can improve performance of Your Zen Cart store.</p>
<p style="text-align: justify;">At this moment there are two components:</p>
<ul style="text-align: justify;">
<li>Basic Logger &#8211; it&#8217;ll display to trusted users all logged queries in Zen Cart shop footer.</li>
<li>Database Logger &#8211; it&#8217;ll save all logged queries to database.</li>
</ul>
<h2 style="text-align: justify;"><strong>Demo Stores</strong></h2>
<p style="text-align: justify;">Because Database Logger does not display anything to users no demo store is available for it.</p>
<p style="text-align: justify;">Here&#8217;s demo store for Basic Logger: <a rel="nofollow" href="http://www.data-diggers.com/contribs/query-log/demo-stores/with-query-log">Basic Logger Demo Store</a></p>
<h2 style="text-align: justify;"><strong>Basic Logger</strong></h2>
<p style="text-align: justify;">Basic Logger for each page request logs all queries sent to database and displays them to trusted users in page footer together with time each query took. It will mark with red color queries that take much more time then average. See <a href="http://www.data-diggers.com/query-log#screencast">screencast</a> to see it in action.</p>
<p style="text-align: justify;"><strong>Note:</strong> Basic Logger is based on contribution made by Chemo for osCommerce, We just added few features to it.</p>
<h2 style="text-align: justify;"><strong>Database Logger</strong></h2>
<p style="text-align: justify;">Database Logger does everything that Basic Logger do. In addition it also saves all queries from all page requests of all visitors in database table. You can then execute various queries to check which queries should be optimized, which pages generates most queries, what is average time spent in database etc.</p>
<p style="text-align: justify;">Database Logger is as fast as possible, it uses MyISAM tables without primary key and indexes to store queries (this means that MySQL server does not spend time updating lookup tables). Also, if MySQL ver. 5.0 or later is available You can use Archive storage engine to compress logs (installation script provides two versions of sql patches, one for MySQL ver. 5.0 or later, and one for earlier versions).</p>
<p style="text-align: justify;"><strong>Warning</strong>: before turning on Database Logger make sure that You know what You&#8217;re doing. Storing all queries in database can take <strong>huge</strong> amounts of disk space.</p>
<p style="text-align: justify;">You can do various things with query_log table, below are few simple use cases.</p>
<p style="text-align: justify;">To list slowest queries execute:</p>
<div class="codesnip-container" >
<div class="sql codesnip" style="font-family:monospace;"><span class="kw1">SELECT</span> <span class="sy0">*</span><br />
<span class="kw1">FROM</span> query_log<br />
<span class="kw1">ORDER</span> <span class="kw1">BY</span> time <span class="kw1">DESC</span><br />
<span class="kw1">LIMIT</span> <span class="nu0">100</span></div>
</div>
<p style="text-align: justify;">You can check what is average time spent in database for each type of page (product_info, index, advanced_search_results etc.):</p>
<div style="text-align: justify;">
<div class="codesnip-container" >
<div class="sql codesnip" style="font-family:monospace;"><span class="kw1">SELECT</span> page<span class="sy0">,</span> AVG<span class="br0">&#40;</span>time<span class="br0">&#41;</span> <span class="kw1">AS</span> <span class="st0">&#8216;average_time&#8217;</span><br />
<span class="kw1">FROM</span> query_log<br />
<span class="kw1">GROUP</span> <span class="kw1">BY</span> page<br />
<span class="kw1">ORDER</span> <span class="kw1">BY</span> average_time <span class="kw1">DESC</span></div>
</div>
</div>
<p style="text-align: justify;">Listing queries executed on &#8216;product_info&#8217; page that takes more then 0.1 sec to complete:</p>
<div style="text-align: justify;">
<div class="codesnip-container" >
<div class="sql codesnip" style="font-family:monospace;"><span class="kw1">SELECT</span> <span class="sy0">*</span><br />
<span class="kw1">FROM</span> query_log<br />
<span class="kw1">WHERE</span> page <span class="sy0">=</span> <span class="st0">&#8216;product_info&#8217;</span><br />
<span class="kw1">AND</span> time <span class="sy0">&gt;=</span> <span class="nu0">0.1</span></div>
</div>
</div>
<h2 style="text-align: justify;"><strong><a name="screencast"></a>Screencast</strong></h2>
<p style="text-align: justify;">Here&#8217;s screencast showing how to install and use Query Log:</p>
<p style="text-align: center;"><a href="http://www.data-diggers.com/contribs/query-log/screencasts/installation/installation.html" target="_blank"><img src="http://www.data-diggers.com/contribs/query-log/screencasts/installation/thumb.jpg" border="0" alt="" /></a></p>
<h2 style="text-align: justify;"><strong>Download</strong></h2>
<p style="text-align: justify;">Here You can download Query Log compatible with all 1.3.x Zen Cart versions.</p>
<p style="text-align: justify;"><a href="http://www.data-diggers.com/contribs/query-log/downloads/querylog-current.zip"><strong><em>Download Query Log</em></strong></a></p>
<h2 style="text-align: justify;"><strong>Installation</strong></h2>
<p style="text-align: justify;">Requirements:</p>
<ul style="text-align: justify;">
<li>You can use Query Log with any version of Zen Cart 1.3.x.</li>
<li>PHP &gt;= 4.x is required.</li>
<li><a href="http://www.data-diggers.com/query-cache">Query Cache</a> is required. If You don&#8217;t want to use Query Cache You have to change <em>includes/classes/db/mysql/query_factory.php</em> to use Query Log</li>
</ul>
<p style="text-align: justify;">Query Log is quite easy to install. First You need to download it. After that extract it with Winzip or something similar and follow instructions below:</p>
<ol style="text-align: justify;">
<li>BACKUP BACKUP BACKUP!</li>
<li>Upload &#8216;includes&#8217; directory (from directory corresponding to Your Zen Cart version) on Your server (via ftp, sftp or any other protocol).</li>
<li>If You use MySQL &gt;=5.0 copy and paste contents of sql_patch_for_mysql_5.x.sql into Store Admin Panel -&gt; Tools -&gt; Install SQL Patches. Execute the script.</li>
<li>If You use MySQL &lt;5.0 copy and paste contents of sql_patch.sql into Store Admin Panel -&gt; Tools -&gt; Install SQL Patches. Execute the script.</li>
<li>Done.</li>
</ol>
<p style="text-align: justify;">If You use custom template add following line to proper tpl_main_page.php somewhere near end of the file:</p>
<div style="text-align: justify;">
<div class="codesnip-container" >
<div class="php codesnip" style="font-family:monospace;"><span class="kw2">&lt;?php</span> display_query_log<span class="br0">&#40;</span><span class="br0">&#41;</span><span class="sy0">;</span> <span class="sy1">?&gt;</span></div>
</div>
</div>
<p style="text-align: justify;">After installation You&#8217;ll need to configure Query Log.</p>
<h2 style="text-align: justify;"><strong>Configuration</strong></h2>
<p style="text-align: justify;">Query Log adds three options to Admin Panel -&gt; Configuration -&gt; Logging:</p>
<ul style="text-align: justify;">
<li>Enable Database Query Log</li>
<li>Display queries to trusted users</li>
<li>Display queries to users with following email addresses (list of trusted users</li>
</ul>
<h3 style="text-align: justify;"><em>Enable Database Query Log</em></h3>
<p style="text-align: justify;">When enabled <strong>all </strong>logged queries will be saved in database in <strong>query_log</strong> table.</p>
<h3 style="text-align: justify;"><em>Display queries to trusted users</em></h3>
<p style="text-align: justify;">Enables Basic Logger. It will display queries only to logged in users with email addresses listed in <em>Display queries to users with following email addresses</em></p>
<h3 style="text-align: justify;"><em>Display queries to users with following email addresses</em></h3>
<p style="text-align: justify;">Comma separated list of emails.</p>
<h2 style="text-align: justify;"><strong>Stay in touch</strong></h2>
<p style="text-align: justify;">If You wish to be notified about new versions of Query Log, use cases, new screen casts or anything else related to Query Log type Your email address below hit &#8216;Subscribe&#8217;. You will only receive news regarding this contribution.</p>
]]></content:encoded>
			<wfw:commentRss>http://www.data-diggers.com/index.php/2008/12/query-log-released/feed/</wfw:commentRss>
		<slash:comments>0</slash:comments>
		</item>
		<item>
		<title>Query Cache for Zen Cart released</title>
		<link>http://www.data-diggers.com/index.php/2008/12/query-cache-for-zen-cart-released/</link>
		<comments>http://www.data-diggers.com/index.php/2008/12/query-cache-for-zen-cart-released/#comments</comments>
		<pubDate>Sat, 13 Dec 2008 22:43:10 +0000</pubDate>
		<dc:creator>admin</dc:creator>
				<category><![CDATA[Performance]]></category>
		<category><![CDATA[Query Cache]]></category>
		<category><![CDATA[screencast]]></category>
		<category><![CDATA[Speed]]></category>
		<category><![CDATA[Zen Cart]]></category>

		<guid isPermaLink="false">http://www.data-diggers.eu/?p=3</guid>
		<description><![CDATA[
			
				
			
		
Update: Query Cache V1.6 has been released &#8211; read here
Query Cache is free, in memory cache designed to work with Zen Cart. It can reduce number of queries sent to database by over 80% (see charts below). Thus, Query Cache  might greatly reduce query execution time and response time of most Zen Cart stores.
You might [...]]]></description>
			<content:encoded><![CDATA[<div class="tweetmeme_button" style="float: right; margin-left: 10px;">
			<a href="http://api.tweetmeme.com/share?url=http%3A%2F%2Fwww.data-diggers.com%2Findex.php%2F2008%2F12%2Fquery-cache-for-zen-cart-released%2F"><br />
				<img src="http://api.tweetmeme.com/imagebutton.gif?url=http%3A%2F%2Fwww.data-diggers.com%2Findex.php%2F2008%2F12%2Fquery-cache-for-zen-cart-released%2F&amp;style=normal" height="61" width="50" /><br />
			</a>
		</div>
<p style="text-align: justify;"><strong>Update</strong>: Query Cache V1.6 has been released &#8211; <a href="http://www.data-diggers.com/query-cache-v1.6-released">read here</a></p>
<p style="text-align: justify;"><strong>Query Cache</strong> is free, in memory cache designed to work with Zen Cart. It can reduce number of queries sent to database by over 80% (see charts below). Thus, Query Cache  might greatly reduce query execution time and response time of most Zen Cart stores.</p>
<p style="text-align: justify;">You might want to jump quickly to see <a href="http://www.data-diggers.com/sites/all/modules/fckeditor/fckeditor/editor/fckeditor.html?InstanceName=oFCK_1&amp;Toolbar=Default#Demo_Stores">Demo Stores</a>. Compare number of queries on each store.</p>
<h2 style="text-align: justify;"><strong>Performance Analysis</strong></h2>
<p style="text-align: justify;">We&#8217;ve ran some tests on demo installment of Zen Cart 1.3.8a which contains just a few products, few categories, one customer and no orders. Still, Zen Cart generated over nine hundred queries (&gt;900!) just to load first page of the demo store (You can check how many queries generates Your store by turning on &#8216;Display Page Parse Time&#8217;, <a href="http://www.data-diggers.com/sites/all/modules/fckeditor/fckeditor/editor/fckeditor.html?InstanceName=oFCK_1&amp;Toolbar=Default#Verify">read more</a>). After that, Query Cache has been installed and it managed to reduce number of queries by half (from 900 to 199 queries approx.).</p>
<p style="text-align: justify;">Other pages where also checked, including: category view page, search results page and &#8217;static&#8217; (more or less) shipping information page. Results are presented on figures below:</p>
<table style="text-align: justify;" border="0" cellspacing="1" cellpadding="1" width="100%">
<tbody>
<tr>
<td align="center" valign="middle"><a rel="lightbox[query-cache]" href="http://www.data-diggers.com/contribs/query-cache/images/home_page.jpg"><img src="http://www.data-diggers.com/contribs/query-cache/images/home_page.jpg" alt="" width="250" height="193" /></a></td>
<td align="center" valign="middle"><a rel="lightbox[query-cache]" href="http://www.data-diggers.com/contribs/query-cache/images/category.jpg"><img src="http://www.data-diggers.com/contribs/query-cache/images/category.jpg" alt="" width="250" height="193" /></a></td>
</tr>
<tr>
<td align="center" valign="middle"><a rel="lightbox[query-cache]" href="http://www.data-diggers.com/contribs/query-cache/images/search_results_new.jpg"><img src="http://www.data-diggers.com/contribs/query-cache/images/search_results_new.jpg" alt="" width="250" height="193" /></a></td>
<td align="center" valign="middle"><a rel="lightbox[query-cache]" href="http://www.data-diggers.com/contribs/query-cache/images/shipping.jpg"><img src="http://www.data-diggers.com/contribs/query-cache/images/shipping.jpg" alt="" width="250" height="193" /></a></td>
</tr>
</tbody>
</table>
<h2 style="text-align: justify;"><strong>Advantages of Query Cache</strong></h2>
<ul style="text-align: justify;">
<li>reduces number of queries sent to database by 80%</li>
<li>it&#8217;s very easy to install (jump to <a href="http://www.data-diggers.com/sites/all/modules/fckeditor/fckeditor/editor/fckeditor.html?InstanceName=oFCK_1&amp;Toolbar=Default#Installation_Instructions">Installation instructions)</a></li>
<li>reduces page generation time, reduces load on database server.</li>
<li>works with all 1.3.x versions of Zen Cart</li>
</ul>
<h2 style="text-align: justify;"><strong>Disadvantages of Query Cache</strong></h2>
<p style="text-align: justify;">As far as We can tell there is only one disadvantage: at this moment Query Cache can&#8217;t detect if database has been changed while php script is running. This means that if, for example, information about product is pulled from database, then product is updated, and retrieved again from database (<strong>all happening in one request</strong>) updated information might not be retrieved (in next request information will be updated).</p>
<h2 style="text-align: justify;"><a name="Download"></a><strong>Download</strong></h2>
<p style="text-align: justify;">Here is package including Query Cache for <strong>ALL</strong> versions of Zen Cart 1.3.x:</p>
<p style="text-align: center;"><a href="http://www.data-diggers.com/contribs/query-cache/downloads/querycache-current.zip"><span style="font-size: larger;"><strong><em>Download Query Cache &#8211; latest version<br />
</em></strong></span></a></p>
<h2 style="text-align: justify;"><a name="Installation_Instructions"></a><strong>Installation Instructions</strong></h2>
<p style="text-align: justify;">First, download contribution <a href="http://www.data-diggers.com/sites/all/modules/fckeditor/fckeditor/editor/fckeditor.html?InstanceName=oFCK_1&amp;Toolbar=Default#Download">here</a>. Extract it with WinZip or something similar. Go to extracted directory. There are few directories named like &#8216;Zen-Cart 1.3.x&#8217; where &#8216;x&#8217; is minor version number of Zen Cart. To install this module:</p>
<ol style="text-align: justify;">
<li>BACKUP BACKUP BACKUP!</li>
<li>Upload &#8216;includes&#8217; directory (from directory corresponding to Your Zen Cart version) on Your server (via ftp, sftp or any other protocol).</li>
<li>Done.</li>
</ol>
<p style="text-align: justify;"><em><strong>Note:</strong></em> Query Cache v1.5 has feature that might slow down Your store if Your web server is <strong>very </strong>slow. In such case You can try to set <em>QC_USE_PRODUCT_QUERY_DETECTION</em> in includes/extra_configures/query_cache.php to FALSE.<br />
This contribution is preconfigured to use <strong>Query Log</strong> _IF_ it&#8217;s available. If Query Log is not installed, Query Cache will still work without any problems (or at least it should;)</p>
<h2 style="text-align: justify;"><a name="Verify"></a> <strong>How to verify that Query Cache Works</strong></h2>
<h1 style="text-align: justify;"><strong> </strong></h1>
<p style="text-align: justify;">Before installing Query Cache check how many queries Your store executes:</p>
<ul style="text-align: justify;">
<li>Enable &#8216;Display The Page Parse Time&#8217; option in Store Admin in Configuration -&gt; Logging.</li>
<li>Go to Your store, scroll down and see how many queries where executed.</li>
</ul>
<p style="text-align: justify;">Now, install Query Cache and visit the same page. Check query count, it should be much lower.</p>
<h2 style="text-align: justify;"><strong>Screencast</strong></h2>
<p style="text-align: justify;">Here is screencast showing how to install this contribution.</p>
<p style="text-align: center;"><a href="http://www.data-diggers.com/contribs/query-cache/screencasts/installation/querycache.html" target="_blank"><img src="http://www.data-diggers.com/contribs/query-cache/screencasts/installation/thumb.jpg" border="0" alt="" /></a></p>
<h2 style="text-align: justify;"><strong><a name="Demo_Stores"></a>Demo Stores</strong></h2>
<p style="text-align: justify;">Here are two Demo Stores:</p>
<p style="text-align: justify;"><a rel="nofollow" href="http://www.data-diggers.com/contribs/query-cache/demo-stores/with-query-cache/">Demo Store with Query Cache installed</a></p>
<p style="text-align: justify;"><a rel="nofollow" href="http://www.data-diggers.com/contribs/query-cache/demo-stores/without-query-cache/">Demo Store without Query Cache installed</a></p>
<p style="text-align: justify;">Take a look at footer of each store. As You can see Query Cache greatly reduced number of executed queries.</p>
<h2 style="text-align: justify;"><strong>Is it free? (Yes)</strong></h2>
<p style="text-align: justify;">Yes, it is. You can use it on unlimited number of sites without any costs. You can redistribute it, change the source code (but leave us as original authors) etc. You can&#8217;t sell it or make any profit of it.</p>
<h2 style="text-align: justify;"><strong>Stay in touch<br />
</strong></h2>
<p style="text-align: justify;">We plan to release new version of Query Cache soon, with some new features that will further reduce number of executed queries and improve performance of Your store. Just type Your address here to be notified of new versions of Query Cache (You&#8217;ll receive only updates on Query Cache). Quick info: We hate spam, Your email will not be given to anyone.</p>
]]></content:encoded>
			<wfw:commentRss>http://www.data-diggers.com/index.php/2008/12/query-cache-for-zen-cart-released/feed/</wfw:commentRss>
		<slash:comments>2</slash:comments>
		</item>
	</channel>
</rss>
