<?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>Edward Yarnold &#187; Tips</title>
	<atom:link href="http://www.edwardyarnold.co.uk/blog/category/tips/feed" rel="self" type="application/rss+xml" />
	<link>http://www.edwardyarnold.co.uk/blog</link>
	<description>PHP &#38; MySQL Web Developer</description>
	<lastBuildDate>Mon, 12 Dec 2011 18:12:49 +0000</lastBuildDate>
	<language>en</language>
	<sy:updatePeriod>hourly</sy:updatePeriod>
	<sy:updateFrequency>1</sy:updateFrequency>
	<generator>http://wordpress.org/?v=3.2.1</generator>
		<item>
		<title>Working from home: Month 1</title>
		<link>http://www.edwardyarnold.co.uk/blog/working-from-home-month-1</link>
		<comments>http://www.edwardyarnold.co.uk/blog/working-from-home-month-1#comments</comments>
		<pubDate>Wed, 31 Aug 2011 07:09:01 +0000</pubDate>
		<dc:creator>Ed Yarnold</dc:creator>
				<category><![CDATA[Me]]></category>
		<category><![CDATA[Remote Working]]></category>
		<category><![CDATA[Tips]]></category>
		<category><![CDATA[Web Development]]></category>

		<guid isPermaLink="false">http://www.edwardyarnold.co.uk/blog/?p=199</guid>
		<description><![CDATA[I have just completed my first full calendar month of the new teleworking arrangement I have with my current employer, so feel it is a good time to write down some of my feelings and detail my experience thus far.  My arrangement is to work remotely for 3 days of my 5 day week, travelling [...]]]></description>
			<content:encoded><![CDATA[<p>I have just completed my first full calendar month of the new teleworking arrangement I have with my current employer, so feel it is a good time to write down some of my feelings and detail my experience thus far.  My arrangement is to work remotely for 3 days of my 5 day week, travelling in to the office on two consecutive days, typically Wednesday and Thursday.  This tends to break up my week very nicely in to easy chunks: Monday-Tuesday at home, Wednesday-Thursday in office, Friday at home, and then the weekend.  This in itself is one of the biggest advantages in my view; I get 3 &#8216;fresh starts&#8217; per week where I can be ultra-productive.  Rarely do I now get &#8216;that Friday Afternoon feeling!   Following are some tips I have if you are about to start working remotely (and a lot of these points apply to freelance workers too)</p>
<h3><span id="more-199"></span>Tip: Have your own work space or room</h3>
<p>In our house I am fortunate enough to have reserved the &#8216;box room&#8217; bedroom for the sole purpose of serving as my office.  This gives me an opportunity to enter &#8216;a work environment&#8217; and close the door on home (and vice versa at the end of each day).  This focuses the mind on work matters and keeps me from being distracted by the massive amount of DIY work that remains incomplete in our house at the moment.  I recall reading articles before I asked for this arrangement with regards to <a href="http://www.alistapart.com/articles/habit-fields/" target="_blank">habit fields</a>, and really am a believer in this concept.  I think I would find remote-working so much more difficult if I had to sit somewhere that also served as a relaxation area.</p>
<h3>Tip: Set up your working environment properly</h3>
<p>Set up your working environment as if you were in an office for a company.  By this, I mean everything; ranging from the bare bones of your work environment to your software setup.  Actually pay attention to health and safety regulations with regards to monitor and keyboard/mouse use; make sure your chair is correctly adjusted (and is adjustable at all! Don&#8217;t work on a dining chair!) &#8211; in my early days as a freelancer I used to sit on a non-adjustable chair for about 5 hours a day and ended up needing physiotherapy on my lower back as I was in utter agony.</p>
<p>Try not to compromise on your software setup either.  Install the same FTP client you use at work, and configure your IDE or text editor in the same way as your work, including indentation and layout settings; it&#8217;s amazing how a little effort to get the environment consistent can make your life so much easier.  My advice extends to, if possible, having a computer for work and a laptop for pleasure.  This further extends the separation of work time and play time; if this is financially not viable then a good compromise is to have two users on your desktop machine; one for work and one for personal use.  I&#8217;ll bet your bookmarks for work in your bookmarks toolbar are substantially different to the bookmarks for home in your home bookmarks toolbar!</p>
<p><strong>Keep work and pleasure separate in your software environment too</strong></p>
<p>Moving on from that point, I used to have all of my bookmarks for freelancing and general interests in one bookmarks toolbar folder, meaning BBC News was mixed up with the PHP Manual and a bookmark to my phpmyadmin directory.  This made it <em>too easy</em> to see the BBC news bookmark and check the news for 5 minutes.  5 minutes turns in to 10, in to 15, etc.  Now, I keep my bookmarks separate, by using different browsers. I use Mozilla Firefox for work; and Firefox only has my work bookmarks in it, and I use Google Chrome for pleasure; this has my personal bookmarks in it.  Largely I won&#8217;t even use my desktop PC for &#8216;play&#8217; or &#8216;relaxation&#8217; and try to reserve that stuff for my laptop.</p>
<h3>Don&#8217;t get work done in your house when you&#8217;re supposed to be working</h3>
<p>For the first two days of the remote working arrangement we had ongoing building work.  It is very difficult indeed to get good runs of concentration with the noise, and interaction with the tradesmen.  If you&#8217;re having any considerable work done to your house my advice would be, if possible, to go in office for that period.  It&#8217;s much quieter and you&#8217;ll be much more productive.</p>
<h3>Communication</h3>
<p>Assuming you are moving from an office environment, you will be used to being tapped on the shoulder and asked questions, and being asked for updates on the state of work on a fairly regular basis.  Though these distractions are often labelled unnecessary and irritating, they naturally lessen in frequency if you&#8217;re not in the office.  This doesn&#8217;t mean that you should make yourself completely impossible to contact!  I ensured I invested in an unlimited call plan on a home number so that I can call the office as frequently as needed to ask questions to which I need immediate answers, and so that the office have a reliable line on which they can contact me.  Thus far I have more than made good use of the phone line!</p>
<p>Your project manager will largely appreciate frequent, detailed updates of your progress.  There&#8217;s nothing worse than having a developer working for a solid few days with no good indication of where they are at with a project.  It&#8217;s good to say &#8220;all&#8217;s going well and we&#8217;re on time&#8221; and it&#8217;s responsible to inform if you&#8217;re having difficulties and look to be struggling to deliver for the target time.</p>
<h3>Work Time</h3>
<p>Something said fairly frequently to me is &#8220;oh so you can work whenever you want then&#8221;.  I&#8217;m not sure that this is entirely true, and my advice would always be to try to be at your desk between the hours that your office would normally be open (in my case 9am to 5pm).  This means:</p>
<ul>
<li>You are contactable via email and on the phone all day, should you be needed.</li>
<li>You maintain a fairly normal working life and have similar spare time as other people (provided your friends work normal hours!)</li>
<li>You are guaranteed to put in the required number of hours per week.</li>
</ul>
<div>I know that I would find it very difficult, for example, to start working at 1pm and work through to 9pm while all of my friends relax and enjoy themselves.  It&#8217;s easy to maintain the discipline of being &#8216;at work&#8217; from 9 until 5!</div>
<h3>Quick advice for those who do freelance work alongside a full time job</h3>
<ul>
<li>The hours of 9am &#8211; 5pm are strictly your company&#8217;s time.  Make your freelance clients aware of this. Break the rule for <strong>noone</strong>.  <em>In my opinion, to freelance when you&#8217;re being paid to work by someone else is criminal!</em></li>
<li>You will find it much more difficult to motivate yourself to freelance after having spent 8 hours each day working in your own house (I used to find working 12 hour days fairly easy if 8 hours were in-office and 4 hours at home).  My solution to this is to work in my office for work, and to move to the sofa on a laptop to freelance.  This does break slightly from my laptop == pleasure rule but at least gives me some separation in terms of the type of work I do!</li>
</ul>
<h3>Summary</h3>
<p>Overall, it took me a week or two to get in to the swing of working remotely full-time, but I&#8217;ve got there now, and it feels good! I get distracted a lot less on an hour-by-hour basis and feel that I get more done in terms of pure development, and also the three segments to each working week really help me with maintaining my productivity at a high level right from Monday morning to Friday afternoon.  For any employee with the option of working remotely: give it a go, but only if you can separate work and home properly!</p>
]]></content:encoded>
			<wfw:commentRss>http://www.edwardyarnold.co.uk/blog/working-from-home-month-1/feed</wfw:commentRss>
		<slash:comments>2</slash:comments>
		</item>
		<item>
		<title>Distractions &#8211; a useful Firefox plugin to stop them in their tracks</title>
		<link>http://www.edwardyarnold.co.uk/blog/distractions-a-useful-firefox-plugin-to-stop-them-in-their-tracks</link>
		<comments>http://www.edwardyarnold.co.uk/blog/distractions-a-useful-firefox-plugin-to-stop-them-in-their-tracks#comments</comments>
		<pubDate>Thu, 31 Mar 2011 08:30:34 +0000</pubDate>
		<dc:creator>Ed Yarnold</dc:creator>
				<category><![CDATA[Productivity]]></category>
		<category><![CDATA[Tips]]></category>
		<category><![CDATA[Web Development]]></category>

		<guid isPermaLink="false">http://www.edwardyarnold.co.uk/blog/?p=183</guid>
		<description><![CDATA[At work, I occasionally found that if faced with a particularly mundane piece of work, or something that dragged out for a long period of time, it would be quite easy to get distracted by popular sites such as twitter, BBC news, engadget and various other tech-related but not entirely productive sites. I thought &#8220;someone [...]]]></description>
			<content:encoded><![CDATA[<p>At work, I occasionally found that if faced with a particularly mundane piece of work, or something that dragged out for a long period of time, it would be quite easy to get distracted by popular sites such as twitter, BBC news, engadget and various other tech-related but not entirely productive sites.</p>
<p>I thought &#8220;someone else must have had this problem&#8221;, and if they hadn&#8217;t, I was going to write a Firefox Add On to help maintain productivity by blocking distraction web sites.  But, alas, someone has beaten me to it! I have found and installed the <a href="https://addons.mozilla.org/en-US/firefox/addon/leechblock/">LeechBlock</a> Firefox add on and it is fantastic. I&#8217;ve added my favourite sites to a list of sites to block at any time that isn&#8217;t a break time (so here, 9-11, 11.15-1, 1.30-3, 3.15-5) and it&#8217;s proven very effective.</p>
]]></content:encoded>
			<wfw:commentRss>http://www.edwardyarnold.co.uk/blog/distractions-a-useful-firefox-plugin-to-stop-them-in-their-tracks/feed</wfw:commentRss>
		<slash:comments>0</slash:comments>
		</item>
		<item>
		<title>Linux: How to recursively download contents of an FTP directory</title>
		<link>http://www.edwardyarnold.co.uk/blog/linux-how-to-recursively-download-contents-of-an-ftp-directory</link>
		<comments>http://www.edwardyarnold.co.uk/blog/linux-how-to-recursively-download-contents-of-an-ftp-directory#comments</comments>
		<pubDate>Tue, 08 Mar 2011 18:21:43 +0000</pubDate>
		<dc:creator>Ed Yarnold</dc:creator>
				<category><![CDATA[Linux Command Line]]></category>
		<category><![CDATA[Tips]]></category>

		<guid isPermaLink="false">http://www.edwardyarnold.co.uk/blog/?p=177</guid>
		<description><![CDATA[I was looking for a quick way to recursively download the entire FTP directory for a site that we are transferring. This was, I found, the easiest and most straightforward way: On the command line interface, assuming you have wget installed, type: wget -r ftp://USERNAME:PASSWORD@mysite.com/ Hit enter and wait while it retrieves everything for you. [...]]]></description>
			<content:encoded><![CDATA[<p>I was looking for a quick way to recursively download the entire FTP directory for a site that we are transferring.  This was, I found, the easiest and most straightforward way:</p>
<p>On the command line interface, assuming you have wget installed, type:</p>
<p><code>wget -r ftp://USERNAME:PASSWORD@mysite.com/</code></p>
<p>Hit enter and wait while it retrieves everything for you.</p>
<p>I did it this way because I didn&#8217;t want to download 4gb of data to upload again, so ran this command direct from the &#8216;production&#8217; server with its stupidly fast internet connection. Hours and hours saved!</p>
]]></content:encoded>
			<wfw:commentRss>http://www.edwardyarnold.co.uk/blog/linux-how-to-recursively-download-contents-of-an-ftp-directory/feed</wfw:commentRss>
		<slash:comments>0</slash:comments>
		</item>
		<item>
		<title>Commenting code &#8211; a minor but invaluable investment of time</title>
		<link>http://www.edwardyarnold.co.uk/blog/commenting-code-invaluable-investment-of-time</link>
		<comments>http://www.edwardyarnold.co.uk/blog/commenting-code-invaluable-investment-of-time#comments</comments>
		<pubDate>Wed, 03 Nov 2010 18:56:04 +0000</pubDate>
		<dc:creator>Ed Yarnold</dc:creator>
				<category><![CDATA[Best Practice]]></category>
		<category><![CDATA[PHP]]></category>
		<category><![CDATA[Tips]]></category>
		<category><![CDATA[Web Development]]></category>

		<guid isPermaLink="false">http://www.edwardyarnold.co.uk/blog/?p=133</guid>
		<description><![CDATA[I&#8217;m a strong believer in code being written in such a way that it is self documenting, but would not use this as an excuse for not adding in English language comments to go alongside the code. After all, comments add a tiny amount to the size of a PHP file and don&#8217;t slow down [...]]]></description>
			<content:encoded><![CDATA[<p>I&#8217;m a strong believer in code being written in such a way that it is self documenting, but would not use this as an excuse for not adding in English language comments to go alongside the code.  After all, comments add a tiny amount to the size of a PHP file and don&#8217;t slow down the application at all.  Also, the English language comments alongside the code can be used to justify decisions or assumptions you have made, which might make the next programmer&#8217;s visit to the file a lot quicker and more productive.</p>
<p><span id="more-133"></span></p>
<h3>Explaining and justifying your decisions</h3>
<p>At the most very basic level, take this bit of code for example:</p>
<p><code>ksort($files);</code></p>
<p>To most PHP developers it is obvious that this bit of code sorts the $files array in key order.  But it is not obvious to any PHP developer *why* I have done this.  Adding a comment to say what I am doing and why would help speed up the recognition of what this code does; but more importantly, explain why this code is here.:</p>
<p><code><br />
/**<br />
 * Sort the $files array in Key order. We want them displayed on the<br />
 * page in added order,  and the $files array is not necessarily<br />
 * sorted in that order before this stage.<br />
 */<br />
ksort($files);<br />
</code></p>
<h3>Using code comments as a tool: Autocompletion</h3>
<p>There are other areas of an application where documentation can be even more useful.  Modern Code Editors and IDEs will read what are called &#8216;<a href="http://en.wikipedia.org/wiki/PHPDoc#DocBlock">docblocks</a>&#8216; at the top of class, method or function definitions and add the information in the docblock in to your autocomplete prompts.  So how do these docblocks work?</p>
<p>Docblocks are generally in this format (opened by /**, closed by */, with a * at the start of every line inbetween) and always apply to the next uncommented line of code.  In this case, the line of code beginning with $page_posted_to = is documented by the docblock above.:</p>
<p><code><br />
/**<br />
 * Determine if the page has been posted to with an action.<br />
 */<br />
$page_posted_to = (array_key_exists('action', $_POST) &#038;&#038; !empty($_POST['action']));<br />
</code></p>
<p>Within docblocks you can contain &#8216;tags&#8217;.  These &#8216;tags&#8217; begin with an @ symbol and are often read or interpreted by documentation generation utilities or IDEs/Editors for autocompletion.  A comprehensive list can be found on the <a href="http://en.wikipedia.org/wiki/PHPDoc#Tags">Wikipedia page for Docblocks</a>.   Using these tags can encourage you to include information in your documentation that you might forget to include normally, ie the expected data type of function parameters.</p>
<p>At it&#8217;s most basic use, docblocks usually look something like this when describing a function or method:</p>
<p><code><br />
/**<br />
 * This function adds two values together<br />
 * @param int $a The first value<br />
 * @param int $b The second value<br />
 * @return int The value of $a + $b<br />
 */<br />
function add_together($a, $b) {<br />
     return $a + $b;<br />
}<br />
</code></p>
<p>As you can see, including these docblocks explains in plain english what the function does, what parameters it expects, and what it will return.  This can save the next developer that reads your code tonnes of time and headaches, but most importantly of all, will make your code editor or IDE (if it supports autocompletion and docblock parsing) much more intelligent when it comes to helping you call your own methods or functions.</p>
]]></content:encoded>
			<wfw:commentRss>http://www.edwardyarnold.co.uk/blog/commenting-code-invaluable-investment-of-time/feed</wfw:commentRss>
		<slash:comments>0</slash:comments>
		</item>
		<item>
		<title>Coding things the quick way &#8211; often a false economy</title>
		<link>http://www.edwardyarnold.co.uk/blog/coding-things-the-quick-way-often-false-economy</link>
		<comments>http://www.edwardyarnold.co.uk/blog/coding-things-the-quick-way-often-false-economy#comments</comments>
		<pubDate>Wed, 04 Aug 2010 07:37:41 +0000</pubDate>
		<dc:creator>Ed Yarnold</dc:creator>
				<category><![CDATA[Best Practice]]></category>
		<category><![CDATA[PHP]]></category>
		<category><![CDATA[Tips]]></category>
		<category><![CDATA[Web Development]]></category>

		<guid isPermaLink="false">http://www.edwardyarnold.co.uk/blog/?p=129</guid>
		<description><![CDATA[I have recently been tasked with making some changes to the central &#8216;library&#8217; of code that an E-Commerce platform is based on.  Essentially, the &#8216;models&#8217; for this application are all in a central, shared location, and all of the &#8216;installations&#8217; of the e-commerce platform have their own set of controllers and views that interact with [...]]]></description>
			<content:encoded><![CDATA[<p>I have recently been tasked with making some changes to the central &#8216;library&#8217; of code that an E-Commerce platform is based on.  Essentially, the &#8216;models&#8217; for this application are all in a central, shared location, and all of the &#8216;installations&#8217; of the e-commerce platform have their own set of controllers and views that interact with these models.  The changes I am making involve making the deletion of products reversible; so instead of actually deleting products and associated assets, a flag is merely set in the database; is_deleted = 1.  This, at first glance, seems to be quite a simple task; alter the database tables to add the extra column in, and make a change to the central models in Model_Product::deleteProduct and any product &#8216;getter&#8217; functions, eg Model_Product::getProductsByCategoryId.  However, due to the way that the platform has been developed and individual customisations to the installations of that platform have been made, things aren&#8217;t quite so simple.</p>
<p><span id="more-129"></span>The idea of the &#8216;architect&#8217; of this system was that any interaction with databases or storage of data; ie the models; would be shared in the central library.  This would mean that changes such as the one I worked on with is_deleted = 1 would be simple and made in one place, and one place only.  A true implementation of the &#8216;Don&#8217;t Repeat Yourself (DRY)&#8217; principle.</p>
<p>The nature of this platform is that it is exactly that. A platform.  This typically means that no two implementations of the platform are identical, so to speak.  The platform is built upon and &#8216;extended&#8217; to do what the individual customers want from their online shop.  This sometimes means that custom product &#8216;getter&#8217; blocks of code are written.  Often, the &#8216;quick and easy&#8217; approach had been taken with these , and they had simply been added as standalone functions in the <strong>individual project&#8217;s library</strong>, called things such as getAllProductsFlaggedAsSpecial()  This obviously meant that when I implemented my is_deleted changes in the central library, and wasn&#8217;t aware of the custom nature of these custom product selectors, the sites that used those custom product selectors continued to display deleted products.  Big oops!</p>
<p>This now means that I will need to go through the individual implementations of the platform, search for any custom product SQL that is being built, and add the AND p.is_deleted = 0 in to them.</p>
<p>This whole problem got my thinking about how I would approach this issue (The need to build custom product getter functions in individual implementations of the platform), and here&#8217;s how I think I&#8217;d do it.</p>
<p>I think I would ensure that all custom product getter functions were in fact methods in an extension of the main Model class that then called a buildWhereClause method that added any global product SQL (eg AND is_deleted = 0) in, like this:</p>
<p><code><br />
class Model_Product extends Base_Model {<br />
...<br />
function buildWhereClause($sql) {<br />
return 'WHERE p.is_deleted = 0 AND '.$sql;<br />
}<br />
...<br />
}<br />
</code></p>
<p><code><br />
class MyShopNameModel_Product extends Model_Product {<br />
function getProductsFlaggedAsSpecial() {<br />
...<br />
$sql = "SELECT * FROM product ".$this-&gt;buildWhereClause('is_special = 1');<br />
...<br />
}<br />
}</code></p>
<p>Essentially, what I learnt here was that the developer to begin with that wrote these &#8216;quick functions&#8217; saved his or herself half an hour or so, but cost me (2-3 years later) a fair amount of time in debugging.  I think this is evidence that coding things the quick way and implementing a fast solution is often a false economy, and someone later in the life of the software will have to spend the time saved (and possibly more) to work around the disadvantages of the quick approach.</p>
]]></content:encoded>
			<wfw:commentRss>http://www.edwardyarnold.co.uk/blog/coding-things-the-quick-way-often-false-economy/feed</wfw:commentRss>
		<slash:comments>2</slash:comments>
		</item>
		<item>
		<title>Some simple steps on the &#8220;front end&#8221; to reduce web page download time</title>
		<link>http://www.edwardyarnold.co.uk/blog/some-simple-steps-to-reduce-web-page-download-time</link>
		<comments>http://www.edwardyarnold.co.uk/blog/some-simple-steps-to-reduce-web-page-download-time#comments</comments>
		<pubDate>Wed, 14 Jul 2010 07:48:13 +0000</pubDate>
		<dc:creator>Ed Yarnold</dc:creator>
				<category><![CDATA[Optimisation]]></category>
		<category><![CDATA[Tips]]></category>
		<category><![CDATA[Web Development]]></category>

		<guid isPermaLink="false">http://www.edwardyarnold.co.uk/blog/?p=125</guid>
		<description><![CDATA[A few years ago, page download time was a big focus for most web developers, as the majority of people connected to the internet were accessing through &#8220;dial up&#8221; connections, which we all remember for their awful connection noises and the horrific download speeds.  But with the development of faster internet connections in the developed [...]]]></description>
			<content:encoded><![CDATA[<p>A few years ago, page download time was a big focus for most web developers, as the majority of people connected to the internet were accessing through &#8220;dial up&#8221; connections, which we all remember for their awful connection noises and the horrific download speeds.  But with the development of faster internet connections in the developed world, the focus on page load times has been sacrificed for nice looking graphics, chunky javascript libraries and massive CSS files.  But there are some quick, simple steps that can be taken to keep all of the improved functionality and look of a web site but reduce the page load time a little.<br />
<span id="more-125"></span><br />
Before I get in to the tips themselves, here are a few basic rules of web site optimisation:</p>
<ul>
<li>HTTP requests are <a href="http://yuiblog.com/blog/2007/01/04/performance-research-part-2/">expensive in terms of time</a>.  Reducing the number speeds page load time.</li>
<li>Browsers can &#8211; and do &#8211; cache effectively.  Inline CSS and Javascript can&#8217;t be cached for later page requests.</li>
<li>Images can be optimised on the web without any major loss in visual quality.</li>
</ul>
<h2>Javascript Files</h2>
<h3>Minify Them!</h3>
<p>Firstly, remember that if you are including libraries such as jQuery, there are a few ways in which you can do so.  They offer a &#8220;minified&#8221; or &#8220;compressed&#8221; version, which is at least half the size in KB of the uncompressed version.  Given that you are extremely unlikely to need to ever modify the jQuery core, I don&#8217;t see any argument for including the full version of the library, and would choose to include the smaller, minified version every time.</p>
<p>If you have your own javascript files that are particularly hefty, you can minify those for production sites too, by using tools such as <a href="http://www.crockford.com/javascript/jsmin.html">JSMin</a>.  The only problem with doing this is you tend to need to maintain two versions of the file.  The minification process tends to be irreversible so you will need to keep a &#8220;development&#8221; copy of the javascript, just in case you need to make changes or additions in the future.</p>
<h3>Use a Content Delivery Network for your javascript libraries!</h3>
<p>If you want to go one step further, you can include libraries such as jQuery from &#8220;Content Delivery Networks&#8221;.  Here is what wikipedia defines a CDN as:</p>
<blockquote><p>A content delivery network or content distribution network (CDN) is a  system of computers containing copies of data, placed at various points  in a network so as to maximize bandwidth for access to the data from  clients throughout the network</p></blockquote>
<p>Put simply, CDNs are probably much more capable of delivering the javascript files to the web browser accessing your page quickly and reliably than your own server.  Additionally, remember that this means that the CDN is taking some of your bandwidth costs away &#8211; at least 50kb per new visitor.  An additional strange secondary advantage is that it is possible that the user has previously visited a page including the javascript library from the same CDN earlier in their internet browsing session, so it will already be cached in their machine, and will not need to be loaded for a second time.</p>
<p>If you are looking for a quick link to the Google Javascript CDN,  you can access it here:</p>
<p><a href="http://code.google.com/apis/ajaxlibs/">http://code.google.com/apis/ajaxlibs/</a></p>
<h3>Include them only when they are needed!</h3>
<p>Imagine that you have a &#8220;google map&#8221; page on your web site that integrates with the Google Maps API.  You have a fairly chunky 15kb Javascript file that handles your personal Google Maps integration, as well as including Google&#8217;s own API file for the maps.  Why would you want this javascript on every page of the site?  A lot of web developers and designers are guilty of putting the javascript in every single page of the site, which means that the request and corresponding bandwidth associated with the maps integration would be used even if the visitor never viewed that area of the site.</p>
<h2>Images</h2>
<p>This section is going to be quite short, as it isn&#8217;t really my department, but my main understanding is:</p>
<ul>
<li>Adobe Photoshop has a save for web feature. Use it.</li>
<li>Application specific META data is not needed in images on the web (I understand that Adobe Photoshop again can be a devil for this). Remove it if you can!</li>
<li>If you have &#8220;hover&#8221; states on buttons or navigation items, use <a href="http://www.alistapart.com/articles/sprites">CSS Sprites</a> rather than two separate images.  The reasons why are explained in the link supplied, but mainly revolve around making the hover work immediately, and reducing the number of HTTP requests.</li>
</ul>
<h2>CSS</h2>
<p>There are two situations here, really.  The majority of the time, most of the CSS will be used on all of the pages of the site, so it makes sense to make this one external cacheable file.  It is important that the CSS isn&#8217;t included in &lt;style type=&#8221;text/css&#8221;&gt;&lt;/style&gt; tags in the document itself, as this information is not cacheable and will be individually reloaded on the following page.</p>
<p>A lot of sites will include two or three CSS files. One for the site itself, and one for a plugin such as &#8220;lightbox&#8221; or &#8220;slimbox&#8221; or something similar.  If lightbox/slimbox is used on most pages, why not combine the CSS files in to one slightly larger one?  This will reduce the number of HTTP requests and put all of the CSS in to a single cached file.</p>
<p>There is an argument, also, that if there is a particularly complicated section of the web site that takes up 10kb of a CSS file all by itself, then that 10kb of the CSS should be split out in to a separate css file and included only in the complicated section, where it is needed.  This kind of optimisation will need to be assessed on a per-case basis!</p>
<p>Finally, remember that css itself can be written efficiently.</p>
<p>Compare these two blocks of code, which do the same thing, and you will see what I mean!</p>
<p><code><br />
margin-top: 10px;<br />
margin-bottom: 15px;<br />
margin-right: 5px;<br />
margin-left: 2px;<br />
</code></p>
<p><code><br />
margin: 10px 5px 15px 2px;</code></p>
<p>In conclusion, the steps above often take less than an hour to implement on a well built web site, and can save a couple of seconds per page load, and a fair amount of bandwidth costs.  With google&#8217;s <a href="http://googlewebmastercentral.blogspot.com/2010/04/using-site-speed-in-web-search-ranking.html">recent introduction of a small focus on page load time in terms of a web site&#8217;s ranking</a>, these kind of improvements have more benefits than just making the site appear faster, and are worth paying some attention!</p>
]]></content:encoded>
			<wfw:commentRss>http://www.edwardyarnold.co.uk/blog/some-simple-steps-to-reduce-web-page-download-time/feed</wfw:commentRss>
		<slash:comments>0</slash:comments>
		</item>
		<item>
		<title>Simple steps towards accurate project estimates</title>
		<link>http://www.edwardyarnold.co.uk/blog/accurate-project-estimates</link>
		<comments>http://www.edwardyarnold.co.uk/blog/accurate-project-estimates#comments</comments>
		<pubDate>Wed, 05 May 2010 17:12:50 +0000</pubDate>
		<dc:creator>Ed Yarnold</dc:creator>
				<category><![CDATA[Best Practice]]></category>
		<category><![CDATA[Project Management]]></category>
		<category><![CDATA[Tips]]></category>
		<category><![CDATA[Web Development]]></category>

		<guid isPermaLink="false">http://www.edwardyarnold.co.uk/blog/?p=104</guid>
		<description><![CDATA[A mistake that many developers (including myself) have made in the past is to over-promise and under-deliver in terms of the absolute deadline or the number of hours taken on a project.  Getting to the &#8220;missing the deadline&#8221; or &#8220;being over budget&#8221; stage can be especially demotivating &#8211; you&#8217;re costing yourself (or your company) time, [...]]]></description>
			<content:encoded><![CDATA[<p>A mistake that many developers (including myself) have made in the past is to over-promise and under-deliver in terms of the absolute deadline or the number of hours taken on a project.  Getting to the &#8220;missing the deadline&#8221; or &#8220;being over budget&#8221; stage can be especially demotivating &#8211; you&#8217;re costing yourself (or your company) time, which is valuable, and also the client is likely to be getting slightly irritated (if you are late).  The steps or methods to reduce the chances of this happening in the first place are simple, and easy to use.<br />
<span id="more-104"></span></p>
<h3>1. Make sure you understand the problem in full.</h3>
<p>Generally, when we are presented with a problem by either a client, or a project manager, the problem has been simplified somewhat.  A 15 minute phone conversation or meeting is condensed in to a three sentence paragraph asking you the best way around a problem.  In my eyes, there are a couple of approaches to avoid this.</p>
<ol>
<li><strong>Be involved in the meeting, or the phone conversation</strong>.  This is not always possible &#8211; not every developer wants to be interrupted every 30 minutes by client questions, and not every developer is necessarily comfortable talking to a client.  But listening in on (and not participating in) a conversation could always be an option!  This means that you get to hear everything that the client has said about the problem.  It&#8217;s to be expected that the person relaying the message will miss out minor (but not necessarily insignificant) details.  After all, repeating every phone conversation in full could get a bit tiresome, you&#8217;d imagine!</li>
<li><strong>Know to ask the right questions.</strong> A client asks to make their delivery fee increase with every product added.  Let&#8217;s say, increase the delivery fee by 30% for every additional product that needs delivering.  This is simple enough, until you consider that the delivery fee could easily escalate way out of control.  A £10 standard delivery fee could soon escalate to around £50 if someone bought a large amount of products.  This could discourage a purchase.  So should a limit be introduced for the maximum delivery fee?  Remember, the client probably hasn&#8217;t thought around this issue.  Asking the question and getting an answer before work starts could save you from having to rewrite a chunk of code.</li>
</ol>
<h3>2. If dealing with unfamiliar technology&#8230; allow some research time!</h3>
<p>If you&#8217;ve been asked to implement an unfamiliar technology, take 10 or 15 minutes to research how it all works.  15 minutes spent now could stop you from estimating that something will take 5 hours when it might take 20, or from estimating 20 hours when it might take 5!   Additionally, when estimating how long the work will take, remember that you will probably spend a fair chunk of time reading documentation and not actually writing code.  In many places this would be considered billable time &#8211; and it should certainly be taken in to account when working out how soon you could deliver the work.</p>
<h3>3.  Remember to allow time for testing and bug fixing.</h3>
<p>Not everyone does this, but in my opinion it is essential.  Allow some time for proper testing and the time it&#8217;ll take to fix bugs (this can only be estimated) as well as the time taken to write the code in the first place.</p>
<h3>4. If dealing with third party services, you can&#8217;t accurately promise a deadline.</h3>
<p>A lot of the work I do involves integration with third party services &#8211; payment gateway services, SMS services, etc.  These all involve an account application and signup process, and sometimes this process depends on the client completing a form, or submitting payment for the service.   I have found that it is almost impossible to accurately estimate a &#8220;go live&#8221; date when an aspect of your application depends on a third party service being ready for use.  If you do provide an estimated go live date, it could be worth putting in a note that it depends on the client&#8217;s service X application being complete by date Y.</p>
<h3>5. If you feel out of your depth, don&#8217;t be afraid to say!</h3>
<p>This is a very important point.  If you are not confident about working with and fully understanding the technology that you will be using, <strong>tell your manager or your client! </strong>It&#8217;s better to say at this stage than to blindly assume that you will be able to work something out during the work.  They will be a darn sight happier this way around than if you go out of your depth and then the project is late or massively over budget.  Saying now typically will have one of three results:</p>
<ol>
<li><strong>Your company will turn the work away</strong> to avoid a problem (or, your client will go elsewhere).</li>
<li><strong>Measures will be put in place to avoid the issue.</strong> Billing by the hour, or using another developer, for instance.</li>
<li><strong>The project will be quoted anyway at an estimated rate, and your company will take a risk.</strong> In this case, you at least said something at the start &#8211; the risk taken was by someone above you.</li>
</ol>
<p>These are only very basic steps that can be taken to avoid a problem.  But one thing is for certain.  It is typically better to <strong>under promise and over deliver</strong> rather than the other way around.  You just have to be careful that you don&#8217;t fall in to the habit of *massively* over-quoting projects, because this can have a detrimental effect in terms of reducing the percentage of accepted quotations.</p>
]]></content:encoded>
			<wfw:commentRss>http://www.edwardyarnold.co.uk/blog/accurate-project-estimates/feed</wfw:commentRss>
		<slash:comments>0</slash:comments>
		</item>
		<item>
		<title>Should you sanitise your HTML before or after you save to your database?</title>
		<link>http://www.edwardyarnold.co.uk/blog/when-to-sanitise-data</link>
		<comments>http://www.edwardyarnold.co.uk/blog/when-to-sanitise-data#comments</comments>
		<pubDate>Mon, 19 Apr 2010 12:52:58 +0000</pubDate>
		<dc:creator>Ed Yarnold</dc:creator>
				<category><![CDATA[Best Practice]]></category>
		<category><![CDATA[PHP]]></category>
		<category><![CDATA[Tips]]></category>
		<category><![CDATA[Web Development]]></category>

		<guid isPermaLink="false">http://www.edwardyarnold.co.uk/blog/?p=85</guid>
		<description><![CDATA[In starting a new project completely from scratch we need to decide whether to sanitise html (that is, convert &#38; to &#38;amp;, &#60; to &#38;lt;, and strip out blacklisted html) before or after we saved to database.  In projects I&#8217;d worked on in the past this had been done inconsistently in different areas of the [...]]]></description>
			<content:encoded><![CDATA[<p>In starting a new project completely from scratch we need to decide whether to sanitise html (that is, convert &amp; to <code>&amp;amp;</code>, &lt; to <code>&amp;lt;</code>, and strip out blacklisted html) before or after we saved to database.  In projects I&#8217;d worked on in the past this had been done inconsistently in different areas of the application &#8211; ie, pre save in some areas and on select in others.  After having thought through the problem I think I&#8217;ve decided on which option I prefer: Sanitise after selecting from the database, rather than before saving to the database.</p>
<p><span id="more-85"></span>My reasons for this decision are as follows:</p>
<ol>
<li><strong>Database collation</strong>.  Searching for strings <code>LIKE '%Ed, Ed &amp; Eddie%'</code> starts to get complicated if you have converted &amp; to &amp;amp; &#8211; you have to remember to convert entities in your search string as well.  This could also potentially mess up the effect ORDER BY clauses in the SQL queries you write have on the dataset.</li>
<li><strong>Data Integrity</strong>.  If in the future I decide that I all HTML, or just specific previously blacklisted HTML tags to be allowed, the data is all still complete and certain aspects of the data have not been removed.</li>
<li><strong>Application Consistency</strong>.  I know that if I am ever displaying data selected from the database it will need to be &#8216;sanitised&#8217; before being displayed to the user either in repopulated &#8216;edit&#8217; forms or in a normal &#8216;view&#8217; type screen.</li>
</ol>
<p>I also did a little bit of research in the cakephp manual (as we will be using cakephp for this next project) to see what cakephp creators thought about this and it seems they reached the same conclusion (quoted from <a href="http://book.cakephp.org/view/153/Data-Sanitization">this page</a>):</p>
<blockquote><p>For sanitization against XSS its generally better to save raw HTML in  database without modification and sanitize at the time of  output/display.</p></blockquote>
<p>They don&#8217;t give any specific reasons but I imagine that their thought process was similar to mine.</p>
]]></content:encoded>
			<wfw:commentRss>http://www.edwardyarnold.co.uk/blog/when-to-sanitise-data/feed</wfw:commentRss>
		<slash:comments>2</slash:comments>
		</item>
		<item>
		<title>How I organise my project information to save time.</title>
		<link>http://www.edwardyarnold.co.uk/blog/organisation-time-saving</link>
		<comments>http://www.edwardyarnold.co.uk/blog/organisation-time-saving#comments</comments>
		<pubDate>Mon, 12 Apr 2010 06:16:19 +0000</pubDate>
		<dc:creator>Ed Yarnold</dc:creator>
				<category><![CDATA[Best Practice]]></category>
		<category><![CDATA[Tips]]></category>
		<category><![CDATA[Web Development]]></category>

		<guid isPermaLink="false">http://www.edwardyarnold.co.uk/blog/?p=51</guid>
		<description><![CDATA[It shouldn&#8217;t be news to anyone, but organising your projects (and assets within those projects) in an efficient manner will save you a load of time.   Perhaps not immediately, but at some point in the future you&#8217;ll be thanking yourself hundreds of times over that you took the time to organise things in the first [...]]]></description>
			<content:encoded><![CDATA[<p>It shouldn&#8217;t be news to anyone, but organising your projects (and assets within those projects) in an efficient manner will save you a load of time.   Perhaps not immediately, but at some point in the future you&#8217;ll be thanking yourself hundreds of times over that you took the time to organise things in the first place.</p>
<p><span id="more-51"></span>Starting with the basics, organisation in projects can be as simple as ensuring that you store all information supplied by the client with the project, in a folder called something like &#8216;assets&#8217;.   Typically I would split them by asset type &#8211; images for web, images for print, documents for web download, internal documents, other &#8211; and perhaps include a &#8216;supply date&#8217; in the filename of each.</p>
<p>Next, write stuff down!  If a particular part of the project depends on an external service being available, write this down in a document that stays with the project wherever it goes.  Any useful information that is in your head the day you write the code for the project should probably be written down.  You more than likely won&#8217;t remember in 2 years time when something goes wrong!  All of this information could simply be stored in a README file.</p>
<p>Good organisation doesn&#8217;t boil down to simply putting things in to folders, or keeping notes.  Of course, these actions are a part of the organisation, but don&#8217;t cover everything.  More importantly &#8211; especially in the IT industry &#8211; consistency can be the best time saving characteristic you can introduce to your work.  Being consistent is almost synonymous with being organised when it comes to your project management&#8230;</p>
<p>I save time (and frustration!) by:</p>
<ul>
<li>Naming projects consistently.  My project name tends to match the main part of the domain name on which the web site or project will be hosted.  If I&#8217;ve a domain called edwardyarnold.co.uk, the project in my subversion repository will be called edwardyarnold.  This makes it a lot quicker to put my hand on the correct project if a change needs to be made.</li>
<li>Naming the associated MySQL databases consistently.  For the above project, the CMS database would be called edwardyarnold_cms.  If the site were an ecommerce site, it would be called edwardyarnold_ecom.  This makes finding the relevant database in a phpmyadmin screen much quicker than if the databases weren&#8217;t named consistently.</li>
<li>Ensuring that if a project is replaced with an entirely new version, it is archived with a date.  If I replaced the edwardyarnold.co.uk site with a completely new build, I&#8217;d move the current project to edwardyarnold_2010_archive and create a new one to replace the old.  This is a better approach to dating the new version of the site &#8211; the new version of the site would still exist in 2011 but would appear to be out of date if dated 2010.  Annoying to anyone who didn&#8217;t know that that was the &#8216;latest&#8217; version of the site.</li>
<li>Naming administration area directories according to a set naming pattern (I won&#8217;t disclose that here).  This means that anyone who I work with that knows the pattern can find the administration area without looking up the directory name.  (They will of course have to look up the username and password, if not saved in their browser).</li>
</ul>
<p>These save a tiny amount of time individually, but collectively &#8211; and applied over multiple projects &#8211; the tiny amounts of time soon add up, and you can start to actually notice the saving.  Additionally, following these &#8216;rules&#8217; means that new people joining your team can begin to understand and get a grip of the way you work quicker than if everything was done differently for each project.  In larger organisations this can reduce recruitment costs (remember, downtime whilst training your new staff member is a hidden recruitment cost&#8230;!) as well as saving your existing team time.</p>
]]></content:encoded>
			<wfw:commentRss>http://www.edwardyarnold.co.uk/blog/organisation-time-saving/feed</wfw:commentRss>
		<slash:comments>1</slash:comments>
		</item>
		<item>
		<title>PHP Developers (and Web Design companies): Consider using someone else to check your work!</title>
		<link>http://www.edwardyarnold.co.uk/blog/php-developers-and-web-design-companies-consider-using-someone-else-to-check-your-work</link>
		<comments>http://www.edwardyarnold.co.uk/blog/php-developers-and-web-design-companies-consider-using-someone-else-to-check-your-work#comments</comments>
		<pubDate>Mon, 22 Mar 2010 22:00:42 +0000</pubDate>
		<dc:creator>Ed Yarnold</dc:creator>
				<category><![CDATA[Best Practice]]></category>
		<category><![CDATA[Tips]]></category>
		<category><![CDATA[Web Development]]></category>

		<guid isPermaLink="false">http://www.edwardyarnold.co.uk/blog/?p=31</guid>
		<description><![CDATA[We&#8217;ve all been there.  Working flat out on a project for day after day, to finally see the light at the end of the tunnel and start to consider launching.  But wait!  This is a dangerous situation to be in.  Having looked at the same site for so long, you&#8217;re not going to be able [...]]]></description>
			<content:encoded><![CDATA[<p>We&#8217;ve all been there.  Working flat out on a project for day after day, to finally see the light at the end of the tunnel and start to consider launching.  But wait!  This is a dangerous situation to be in.  Having looked at the same site for so long, you&#8217;re not going to be able to spot the mistakes that you&#8217;ve made.  It&#8217;s worth spending an extra couple of hours to double-check your work &#8211; rather than have the embarassing situation of launching a site with mistakes present.</p>
<p><span id="more-31"></span>Until I worked for a couple of established Web Development companies, I never realised the importance of a &#8216;Checklist&#8217; at the end of a project.  You know, simple things.  Does the site&#8217;s markup validate?  Do all images have alt tags?  Is php display_errors off?  But even after getting in the habit of ticking all of the items off this checklist for every site I build, there are still little mistakes that creep through &#8211; miscapitalised letters, incorrectly pluralised nouns&#8230; eg &#8220;There are 1 comments on this post&#8221; should be &#8220;There is 1 comment on this post&#8221;.   No checklist can possibly cover all of these possible errors (though the one I link to later in this post gives it a good go!).</p>
<p>The best way of discovering these problems is to ask a favour of (or even to employ) someone you know &#8211; preferably without a technical background &#8211; to go through the site and see if they can spot anything that needs changing or fixing.  You will find that they will probably produce a list twice as long as your original checklist!</p>
<p>The beauty of this approach is &#8211; as well as spotting spelling mistakes and other simple errors &#8211; you may also get some <strong>vital</strong> usability feedback, especially if you are with them when they are checking the site.  Do they seem frustrated? Did they use the site in the manner you would expect them to?</p>
<p>I was once fortunate enough to be behind a one-way mirror in a usability testing session and it was simply amazing.  We had a captcha image on a form (I know, I know.. don&#8217;t start) and the error message was misunderstood or found to be confusing by nearly every user.  The abandonment (and frustration) rate on the contact form <a href="http://www.webmasterworld.com/new_web_development/3463891.htm">was therefore extremely high</a>.  This kind of problem would not normally be picked up in smaller projects where a usability testing session is not included (and you wrote the error message &#8211; so find it simple, right?), but if you run through the site with someone to whom the site is fresh, there&#8217;s a much higher chance that you will pick up the problem.  Remember that this issue wouldn&#8217;t be picked up by a checklist either!</p>
<p>So.. checking through a site with somebody non-technical (and who has never seen the site before) can save you a whole bunch of headaches in the future.  And remember &#8211; if you&#8217;re launching your web sites without a <a href="http://www.boxuk.com/blog/the-ultimate-website-launch-checklist">flight check list (check this one out from Box UK)</a>, that&#8217;s probably one of the first things you should consider implementing in your project schedule.  It will save you a lot more support time than it costs you.</p>
]]></content:encoded>
			<wfw:commentRss>http://www.edwardyarnold.co.uk/blog/php-developers-and-web-design-companies-consider-using-someone-else-to-check-your-work/feed</wfw:commentRss>
		<slash:comments>2</slash:comments>
		</item>
	</channel>
</rss>

