<?xml version='1.0' encoding='UTF-8'?><?xml-stylesheet href="http://www.blogger.com/styles/atom.css" type="text/css"?><feed xmlns='http://www.w3.org/2005/Atom' xmlns:openSearch='http://a9.com/-/spec/opensearchrss/1.0/' xmlns:blogger='http://schemas.google.com/blogger/2008' xmlns:georss='http://www.georss.org/georss' xmlns:gd="http://schemas.google.com/g/2005" xmlns:thr='http://purl.org/syndication/thread/1.0'><id>tag:blogger.com,1999:blog-21967381</id><updated>2026-04-10T20:10:31.239+00:00</updated><category term="Testing"/><category term="TDD"/><category term="MbUnit"/><category term="SQL Server"/><category term="DDD"/><category term="Linq"/><category term="C#"/><category term="IronRuby"/><category term="alt.net.uk"/><category term="Alt.net"/><category term="Red Gate"/><category term="Visual Studio 2008"/><category term="LiveWriter"/><category term="NxtGenUG"/><category term="Ruby"/><category term="DLR"/><category term="ASP.net MVC"/><category term="Bad Software"/><category term="Blogging"/><category term="DDD6"/><category term="Pex"/><category term="SQLBits"/><category term="Sandcastle"/><category term="TeamCity"/><category term="TestingASPnet"/><category term="XUnit"/><category term="Community"/><category term="IronPython"/><category term="MSBuild"/><category term="WatiN"/><category term="nodejs"/><category term="ADO.Net Entity Framework"/><category term="DDD7"/><category term="DDS"/><category term="Documentation"/><category term="Katmai"/><category term="MEF"/><category term="Mono"/><category term="Rhino Mocks"/><category term="RubyOnRails"/><category term="CodePlex"/><category term="DDDIreland"/><category term="Git"/><category term="Hadoop"/><category term="Heroku"/><category term="IronEditor"/><category term="Javascript"/><category term="Personal"/><category term="ReSharper"/><category term="SQL Server 2008"/><category term="SubSonic"/><category term="Vista"/><category term="Windows 2008"/><category term="maydayhq"/><category term="BDD"/><category term="Best Practices"/><category term="CCNet"/><category term="Certification"/><category term="FaultInjection"/><category term="GitHub"/><category term="Hardware"/><category term="Jetbrains"/><category term="MVC"/><category term="NUnit"/><category term="PDC08"/><category term="Pik"/><category term="Project White"/><category term="QCon"/><category term="Reflector"/><category term="Silverlight"/><category term="TechEd"/><category term="Twitter"/><category term="Visual Studio"/><category term="book"/><category term="cucumber"/><category term="meerkatalyst"/><category term="AWS"/><category term="Bad Coding"/><category term="Castle"/><category term="CouchDB"/><category term="DDD5"/><category term="DDD8"/><category term="DDDBelfast"/><category term="DDDNorth"/><category term="DDDSW"/><category term="Development"/><category term="Gallio"/><category term="Gaming"/><category term="Google Analytics"/><category term="ICanHazJS"/><category term="Imagine Cup"/><category term="MDN"/><category term="MVP"/><category term="Metallica"/><category term="Microsoft"/><category term="MonoTouch"/><category term="MySql"/><category term="NDC2010"/><category term="NoSQL"/><category term="PromoteJS"/><category term="RSpec"/><category term="Random"/><category term="SSH"/><category term="SVN"/><category term="Screencasts"/><category term="Second Life"/><category term="Simple Talk"/><category term="SocialMedia"/><category term="Spotify"/><category term="Student"/><category term="Ubuntu"/><category term="VB.net"/><category term="VistaSquad"/><category term="Visual Studio 2010"/><category term="Windows Mobile"/><category term="Windows Programming"/><category term="Windows7"/><category term="commands"/><category term="dddie"/><category term="deskspace"/><category term="expressjs"/><category term="given.org"/><category term="grep"/><category term="jQuery"/><category term="launch48"/><category term="lonestar"/><category term="redis"/><category term="sed"/><category term="sxsw"/><category term="sxsw2012"/><category term="unix"/><category term="yodm 3d"/><title type='text'>Ben Hall&#39;s Blog</title><subtitle type='html'>I don&#39;t know darling....i&#39;m doing my work</subtitle><link rel='http://schemas.google.com/g/2005#feed' type='application/atom+xml' href='http://blog.benhall.me.uk/feeds/posts/default'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/21967381/posts/default?redirect=false'/><link rel='alternate' type='text/html' href='http://blog.benhall.me.uk/'/><link rel='hub' href='http://pubsubhubbub.appspot.com/'/><link rel='next' type='application/atom+xml' href='http://www.blogger.com/feeds/21967381/posts/default?start-index=26&amp;max-results=25&amp;redirect=false'/><author><name>Ben Hall</name><uri>http://www.blogger.com/profile/17734933641904484310</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='23' height='32' src='//blogger.googleusercontent.com/img/b/R29vZ2xl/AVvXsEiAHZKs2vYlTA1W58oZ3_laZ-JNsUCxXJj__UyIx7TgHEw6DD9nNDr5ML4vvTpu7HbXx0Q5FIWAXyJ2xRsiX97Iu12TNYdSZuMywoqD7Khsbz936TzlIJOBTkDINgB1iYc/s220/n792665715_5219640_7493.jpg'/></author><generator version='7.00' uri='http://www.blogger.com'>Blogger</generator><openSearch:totalResults>533</openSearch:totalResults><openSearch:startIndex>1</openSearch:startIndex><openSearch:itemsPerPage>25</openSearch:itemsPerPage><entry><id>tag:blogger.com,1999:blog-21967381.post-805743649158645183</id><published>2013-01-14T18:59:00.000+00:00</published><updated>2013-01-14T18:59:03.962+00:00</updated><title type='text'>With the launch of branch I&#39;m considering writing again</title><content type='html'>&lt;script type=&quot;text/javascript&quot; src=&quot;http://embed-script.branch.com/assets/embed/embed.m.js?body=0&quot; data-branch-embedid=&quot;honw_VayjcU&quot; &gt;&lt;/script&gt;&lt;br /&gt;
&lt;noscript&gt;&lt;a href=&quot;http://branch.com/b/me-writing-again&quot;&gt;Me writing again&lt;/a&gt;&lt;/noscript&gt;&lt;br /&gt;
</content><link rel='replies' type='application/atom+xml' href='http://blog.benhall.me.uk/feeds/805743649158645183/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment/fullpage/post/21967381/805743649158645183' title='2 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/21967381/posts/default/805743649158645183'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/21967381/posts/default/805743649158645183'/><link rel='alternate' type='text/html' href='http://blog.benhall.me.uk/2013/01/with-launch-of-branch-im-considering.html' title='With the launch of branch I&#39;m considering writing again'/><author><name>Ben Hall</name><uri>http://www.blogger.com/profile/17734933641904484310</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='23' height='32' src='//blogger.googleusercontent.com/img/b/R29vZ2xl/AVvXsEiAHZKs2vYlTA1W58oZ3_laZ-JNsUCxXJj__UyIx7TgHEw6DD9nNDr5ML4vvTpu7HbXx0Q5FIWAXyJ2xRsiX97Iu12TNYdSZuMywoqD7Khsbz936TzlIJOBTkDINgB1iYc/s220/n792665715_5219640_7493.jpg'/></author><thr:total>2</thr:total></entry><entry><id>tag:blogger.com,1999:blog-21967381.post-7067640542071048706</id><published>2012-10-06T11:35:00.001+00:00</published><updated>2012-10-06T11:35:28.777+00:00</updated><title type='text'>Install Apache and PHP on OSX 10.8 Mountain Lion</title><content type='html'>This is a great post on how to setup and configure Apache and PHP on OSX 10.8.&lt;br /&gt;
&lt;br /&gt;
http://coolestguyplanettech.com/downtown/install-and-configure-apache-mysql-php-and-phpmyadmin-osx-108-mountain-lion&lt;br /&gt;
&lt;br /&gt;</content><link rel='replies' type='application/atom+xml' href='http://blog.benhall.me.uk/feeds/7067640542071048706/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment/fullpage/post/21967381/7067640542071048706' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/21967381/posts/default/7067640542071048706'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/21967381/posts/default/7067640542071048706'/><link rel='alternate' type='text/html' href='http://blog.benhall.me.uk/2012/10/install-apache-and-php-on-osx-108.html' title='Install Apache and PHP on OSX 10.8 Mountain Lion'/><author><name>Ben Hall</name><uri>http://www.blogger.com/profile/17734933641904484310</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='23' height='32' src='//blogger.googleusercontent.com/img/b/R29vZ2xl/AVvXsEiAHZKs2vYlTA1W58oZ3_laZ-JNsUCxXJj__UyIx7TgHEw6DD9nNDr5ML4vvTpu7HbXx0Q5FIWAXyJ2xRsiX97Iu12TNYdSZuMywoqD7Khsbz936TzlIJOBTkDINgB1iYc/s220/n792665715_5219640_7493.jpg'/></author><thr:total>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-21967381.post-8648325543192787097</id><published>2012-07-18T14:34:00.003+00:00</published><updated>2012-07-18T14:34:36.262+00:00</updated><title type='text'>Looking for a developer to join the team in London</title><content type='html'>&lt;span style=&quot;background-color: white;&quot;&gt;I&#39;m currently recruiting for a new C# developer to join the team in London. &amp;nbsp;We&#39;re growing quickly and are looking for developers who want to build products that will people &lt;/span&gt;&lt;i style=&quot;background-color: white; font-weight: bold;&quot;&gt;love&lt;/i&gt;&lt;span style=&quot;background-color: white;&quot;&gt;.&lt;/span&gt;&lt;br /&gt;
&lt;br /&gt;
More details on the role can be found here:&lt;br /&gt;
&lt;a href=&quot;http://bit.ly/NhNCYc&quot;&gt;http://bit.ly/NhNCYc&lt;/a&gt;&lt;br /&gt;
&lt;br /&gt;
If you&#39;re interested in applying then please contact us via the link above or directly via Blog {at} BenHall.me.uk&lt;br /&gt;
&lt;br /&gt;</content><link rel='replies' type='application/atom+xml' href='http://blog.benhall.me.uk/feeds/8648325543192787097/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment/fullpage/post/21967381/8648325543192787097' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/21967381/posts/default/8648325543192787097'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/21967381/posts/default/8648325543192787097'/><link rel='alternate' type='text/html' href='http://blog.benhall.me.uk/2012/07/looking-for-developer-to-join-team-in.html' title='Looking for a developer to join the team in London'/><author><name>Ben Hall</name><uri>http://www.blogger.com/profile/17734933641904484310</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='23' height='32' src='//blogger.googleusercontent.com/img/b/R29vZ2xl/AVvXsEiAHZKs2vYlTA1W58oZ3_laZ-JNsUCxXJj__UyIx7TgHEw6DD9nNDr5ML4vvTpu7HbXx0Q5FIWAXyJ2xRsiX97Iu12TNYdSZuMywoqD7Khsbz936TzlIJOBTkDINgB1iYc/s220/n792665715_5219640_7493.jpg'/></author><thr:total>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-21967381.post-6353379815002433160</id><published>2012-02-01T16:00:00.000+00:00</published><updated>2012-02-01T16:15:35.807+00:00</updated><category scheme="http://www.blogger.com/atom/ns#" term="nodejs"/><title type='text'>Storing Node.js application config data</title><content type='html'>I&#39;ve tried multiple approaches to storing application configuration with Node.js but most have been painful until I found this solution.&lt;br /&gt;
&lt;br /&gt;
&lt;i&gt;tl;dr: Executable configuration FTW via exports.&lt;/i&gt;&lt;br /&gt;
&lt;br /&gt;
With Node.js you can export an object or function for use within another module. This is key to keeping your Node.js application readable and&amp;nbsp;structured&amp;nbsp;which as I&#39;ve found can be an art-form in itself.&lt;br /&gt;
&lt;br /&gt;
&lt;b&gt;My current approach is as follows.&lt;/b&gt;&lt;br /&gt;
&lt;br /&gt;
I have a config.js which looks like this.&lt;br /&gt;
&lt;br /&gt;
&lt;span style=&quot;font-family: &#39;Courier New&#39;, Courier, monospace;&quot;&gt;var url = require(&#39;url&#39;)&lt;/span&gt;&lt;br /&gt;
&lt;span style=&quot;font-family: &#39;Courier New&#39;, Courier, monospace;&quot;&gt;&lt;br /&gt;&lt;/span&gt;&lt;br /&gt;
&lt;span style=&quot;font-family: &#39;Courier New&#39;, Courier, monospace;&quot;&gt;var config = {}&lt;/span&gt;&lt;br /&gt;
&lt;span style=&quot;font-family: &#39;Courier New&#39;, Courier, monospace;&quot;&gt;&lt;br /&gt;&lt;/span&gt;&lt;br /&gt;
&lt;span style=&quot;font-family: &#39;Courier New&#39;, Courier, monospace;&quot;&gt;config.google = {};&lt;/span&gt;&lt;br /&gt;
&lt;span style=&quot;font-family: &#39;Courier New&#39;, Courier, monospace;&quot;&gt;config.redis = {};&lt;/span&gt;&lt;br /&gt;
&lt;span style=&quot;font-family: &#39;Courier New&#39;, Courier, monospace;&quot;&gt;&lt;br /&gt;&lt;/span&gt;&lt;br /&gt;
&lt;span style=&quot;font-family: &#39;Courier New&#39;, Courier, monospace;&quot;&gt;config.google.id = process.env.GOOGLE_ID || &#39;DEVELOPMENT.googleusercontent.com&#39;;&lt;/span&gt;&lt;br /&gt;
&lt;span style=&quot;font-family: &#39;Courier New&#39;, Courier, monospace;&quot;&gt;config.google.secret= &amp;nbsp;process.env.GOOGLE_SECRET || &#39;DEVELOPMENT&#39;;&lt;/span&gt;&lt;br /&gt;
&lt;span style=&quot;font-family: &#39;Courier New&#39;, Courier, monospace;&quot;&gt;config.google.callback= &amp;nbsp;process.env.GOOGLE_CALLBACK || &#39;http://127.0.0.1:3000/google/callback&#39;;&lt;/span&gt;&lt;br /&gt;
&lt;span style=&quot;font-family: &#39;Courier New&#39;, Courier, monospace;&quot;&gt;&lt;br /&gt;&lt;/span&gt;&lt;br /&gt;
&lt;span style=&quot;font-family: &#39;Courier New&#39;, Courier, monospace;&quot;&gt;config.redis.url= &amp;nbsp;url.parse(process.env.REDISTOGO_URL || &#39;http://127.0.0.1:6379&#39;);&lt;/span&gt;&lt;br /&gt;
&lt;span style=&quot;font-family: &#39;Courier New&#39;, Courier, monospace;&quot;&gt;&lt;br /&gt;&lt;/span&gt;&lt;br /&gt;
&lt;span style=&quot;font-family: &#39;Courier New&#39;, Courier, monospace;&quot;&gt;module.exports = config;&lt;/span&gt;&lt;br /&gt;
&lt;br /&gt;
Because it&#39;s a standard JavaScript module, when Node.js loads the file it will be executed with the config hash created. This has two important aspects.&lt;br /&gt;
&lt;br /&gt;
Firstly, I can include other helper modules, such as being able to return a parsed url.&lt;br /&gt;
&lt;br /&gt;
Secondly, I can take advantage of the current environment to determine if production or development values should be returned. This is great when combined with Heroku.&lt;br /&gt;
&lt;br /&gt;
With the configuration defined, the logic to access the configuration looks like this:&lt;br /&gt;
&lt;br /&gt;
&lt;span style=&quot;font-family: &#39;Courier New&#39;, Courier, monospace;&quot;&gt;var config = require(&#39;./config&#39;)&lt;/span&gt;&lt;br /&gt;
&lt;span style=&quot;font-family: &#39;Courier New&#39;, Courier, monospace;&quot;&gt;var id = config.google.id&lt;/span&gt;&lt;br /&gt;
&lt;span style=&quot;font-family: &#39;Courier New&#39;, Courier, monospace;&quot;&gt;var url = config.redis.url&lt;/span&gt;&lt;br /&gt;
&lt;br /&gt;
No if statements, no redefining variables, no swapping files around.&amp;nbsp;Clean, simple, effective. &lt;br /&gt;
&lt;br /&gt;
If I wanted to have additional confidence then if&amp;nbsp;NODE_ENV equaled production I could&amp;nbsp;ensure all environment variables are not undefined.&lt;br /&gt;
&lt;br /&gt;
This is working for me, but has anyone found any better solutions? Leave a comment or tweet me &lt;a href=&quot;http://twitter.com/ben_hall&quot;&gt;@Ben_Hall&lt;/a&gt;&lt;br /&gt;
&lt;br /&gt;</content><link rel='replies' type='application/atom+xml' href='http://blog.benhall.me.uk/feeds/6353379815002433160/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment/fullpage/post/21967381/6353379815002433160' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/21967381/posts/default/6353379815002433160'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/21967381/posts/default/6353379815002433160'/><link rel='alternate' type='text/html' href='http://blog.benhall.me.uk/2012/02/storing-application-config-data-in.html' title='Storing Node.js application config data'/><author><name>Ben Hall</name><uri>http://www.blogger.com/profile/17734933641904484310</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='23' height='32' src='//blogger.googleusercontent.com/img/b/R29vZ2xl/AVvXsEiAHZKs2vYlTA1W58oZ3_laZ-JNsUCxXJj__UyIx7TgHEw6DD9nNDr5ML4vvTpu7HbXx0Q5FIWAXyJ2xRsiX97Iu12TNYdSZuMywoqD7Khsbz936TzlIJOBTkDINgB1iYc/s220/n792665715_5219640_7493.jpg'/></author><thr:total>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-21967381.post-6167590555739568321</id><published>2012-01-31T16:00:00.000+00:00</published><updated>2012-02-01T16:12:51.851+00:00</updated><category scheme="http://www.blogger.com/atom/ns#" term="Heroku"/><category scheme="http://www.blogger.com/atom/ns#" term="nodejs"/><category scheme="http://www.blogger.com/atom/ns#" term="redis"/><title type='text'>Using Redis and RedisToGo to store Node.js sessions on Heroku</title><content type='html'>Storing data in the session state is a little bit naughty as HTTP should remain stateless but there is a trade-off. In this case I wanted to test an assumption around a potential&amp;nbsp;feature for&amp;nbsp;&lt;a href=&quot;http://www.maydayhq.com/&quot; target=&quot;_blank&quot;&gt;Mayday&lt;/a&gt;.&amp;nbsp;I felt&amp;nbsp;it was more important to release than over architecture the entire solution with the&amp;nbsp;possibility&amp;nbsp;of dropping the &amp;nbsp;feature the next day.&lt;br /&gt;
&lt;br /&gt;
When it comes to Node.js, session state is stored in-memory meaning any restarts or new deployments will delete the data.&lt;br /&gt;
&lt;br /&gt;
&lt;b&gt;Enter Redis&lt;/b&gt;&lt;br /&gt;
&lt;br /&gt;
Redis is an ultra-fast, open source, advanced key-value store. To make it even easier, RedisToGo offer a hosted version with a &lt;a href=&quot;https://addons.heroku.com/redistogo&quot; target=&quot;_blank&quot;&gt;Heroku plugin&lt;/a&gt;. After adding the plugin, an account will be created with a database URL provided as a configuration variable.&lt;br /&gt;
&lt;br /&gt;
&lt;span style=&quot;font-family: &#39;Courier New&#39;, Courier, monospace;&quot;&gt;$ heroku config&lt;/span&gt;&lt;br /&gt;
&lt;span style=&quot;font-family: &#39;Courier New&#39;, Courier, monospace;&quot;&gt;REDISTOGO_URL &amp;nbsp; =&amp;gt; redis://redistogo:PASSWORD@SERVER.redistogo.com:9712/&lt;/span&gt;&lt;br /&gt;
&lt;span style=&quot;font-family: &#39;Courier New&#39;, Courier, monospace;&quot;&gt;NODE_ENV &amp;nbsp; &amp;nbsp; &amp;nbsp; &amp;nbsp;=&amp;gt; production&lt;/span&gt;&lt;br /&gt;
&lt;br /&gt;
To use this as your session store you will need to configure the middleware by defining a RedisStore from the connect-redis npm.&lt;br /&gt;
&lt;br /&gt;
The require statements should look like this:&lt;br /&gt;
&lt;br /&gt;
&lt;span style=&quot;font-family: &#39;Courier New&#39;, Courier, monospace;&quot;&gt;var express = require(&#39;express&#39;);&lt;/span&gt;&lt;br /&gt;
&lt;span style=&quot;font-family: &#39;Courier New&#39;, Courier, monospace;&quot;&gt;var RedisStore = require(&#39;connect-redis&#39;)(express);&lt;/span&gt;&lt;br /&gt;
&lt;br /&gt;
&lt;span style=&quot;font-family: &#39;Courier New&#39;, Courier, monospace;&quot;&gt;var url = require(&#39;url&#39;)&lt;/span&gt;&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
For development you will want to use your local server.&lt;br /&gt;
&lt;span style=&quot;font-family: &#39;Courier New&#39;, Courier, monospace;&quot;&gt;app.configure(&#39;development&#39;, function(){&lt;/span&gt;&lt;span style=&quot;font-family: &#39;Courier New&#39;, Courier, monospace;&quot;&gt;&amp;nbsp; &amp;nbsp; &amp;nbsp; &amp;nbsp; &amp;nbsp;&lt;/span&gt;&lt;br /&gt;
&lt;span style=&quot;font-family: &#39;Courier New&#39;, Courier, monospace;&quot;&gt;&amp;nbsp; app.use(express.session({ secret: &quot;password&quot;,&amp;nbsp;&lt;/span&gt;&lt;br /&gt;
&lt;span style=&quot;font-family: &#39;Courier New&#39;, Courier, monospace;&quot;&gt;&amp;nbsp; &amp;nbsp; &amp;nbsp; &amp;nbsp; &amp;nbsp; &amp;nbsp; &amp;nbsp; &amp;nbsp; &amp;nbsp; &amp;nbsp; &amp;nbsp; &amp;nbsp; &amp;nbsp; &amp;nbsp; store: new RedisStore({&lt;/span&gt;&lt;br /&gt;
&lt;span style=&quot;font-family: &#39;Courier New&#39;, Courier, monospace;&quot;&gt;&amp;nbsp; &amp;nbsp; &amp;nbsp; &amp;nbsp; &amp;nbsp; &amp;nbsp; &amp;nbsp; &amp;nbsp; &amp;nbsp; &amp;nbsp; &amp;nbsp; &amp;nbsp; &amp;nbsp; &amp;nbsp; &amp;nbsp; &amp;nbsp; &amp;nbsp; &amp;nbsp; &amp;nbsp; &amp;nbsp; &amp;nbsp; host: &quot;127.0.0.1&quot;,&lt;/span&gt;&lt;br /&gt;
&lt;span style=&quot;font-family: &#39;Courier New&#39;, Courier, monospace;&quot;&gt;&amp;nbsp; &amp;nbsp; &amp;nbsp; &amp;nbsp; &amp;nbsp; &amp;nbsp; &amp;nbsp; &amp;nbsp; &amp;nbsp; &amp;nbsp; &amp;nbsp; &amp;nbsp; &amp;nbsp; &amp;nbsp; &amp;nbsp; &amp;nbsp; &amp;nbsp; &amp;nbsp; &amp;nbsp; &amp;nbsp; &amp;nbsp; port: &quot;6379&quot;,&lt;/span&gt;&lt;br /&gt;
&lt;span style=&quot;font-family: &#39;Courier New&#39;, Courier, monospace;&quot;&gt;&amp;nbsp; &amp;nbsp; &amp;nbsp; &amp;nbsp; &amp;nbsp; &amp;nbsp; &amp;nbsp; &amp;nbsp; &amp;nbsp; &amp;nbsp; &amp;nbsp; &amp;nbsp; &amp;nbsp; &amp;nbsp; &amp;nbsp; &amp;nbsp; &amp;nbsp; &amp;nbsp; &amp;nbsp; &amp;nbsp; &amp;nbsp; db: &quot;name_of_my_local_db&quot;&lt;/span&gt;&lt;br /&gt;
&lt;span style=&quot;font-family: &#39;Courier New&#39;, Courier, monospace;&quot;&gt;&amp;nbsp; &amp;nbsp; &amp;nbsp; &amp;nbsp; &amp;nbsp; &amp;nbsp; &amp;nbsp; &amp;nbsp; &amp;nbsp; &amp;nbsp; &amp;nbsp; &amp;nbsp; &amp;nbsp; &amp;nbsp; &amp;nbsp; &amp;nbsp; &amp;nbsp; &amp;nbsp; &amp;nbsp; &amp;nbsp; }) &amp;nbsp;&lt;/span&gt;&lt;br /&gt;
&lt;span style=&quot;font-family: &#39;Courier New&#39;, Courier, monospace;&quot;&gt;&amp;nbsp; &amp;nbsp; &amp;nbsp; &amp;nbsp; &amp;nbsp; })&lt;/span&gt;&lt;span style=&quot;font-family: &#39;Courier New&#39;, Courier, monospace;&quot;&gt;);&lt;/span&gt;&lt;br /&gt;
&lt;span style=&quot;font-family: &#39;Courier New&#39;, Courier, monospace;&quot;&gt;});&amp;nbsp;&lt;/span&gt;&lt;br /&gt;
&lt;span style=&quot;font-family: &#39;Courier New&#39;, Courier, monospace;&quot;&gt;&lt;br /&gt;&lt;/span&gt;&lt;br /&gt;
&lt;span style=&quot;font-family: inherit;&quot;&gt;For production you should use the RedisToGo URL provided.&amp;nbsp;&lt;/span&gt;&lt;br /&gt;
&lt;span style=&quot;font-family: &#39;Courier New&#39;, Courier, monospace;&quot;&gt;app.configure(&#39;production&#39;, function(){&lt;/span&gt;&lt;br /&gt;
&lt;span style=&quot;font-family: &#39;Courier New&#39;, Courier, monospace;&quot;&gt;&amp;nbsp;var redisUrl = url.parse(process.env.REDISTOGO_URL);&lt;/span&gt;&lt;br /&gt;
&lt;span style=&quot;font-family: &#39;Courier New&#39;, Courier, monospace;&quot;&gt;&amp;nbsp;var redisAuth = redisUrl.auth.split(&#39;:&#39;);&lt;/span&gt;&lt;br /&gt;
&lt;span style=&quot;font-family: &#39;Courier New&#39;, Courier, monospace;&quot;&gt;&lt;br /&gt;&lt;/span&gt;&lt;br /&gt;
&lt;span style=&quot;font-family: &#39;Courier New&#39;, Courier, monospace;&quot;&gt;&amp;nbsp;app.use(express.session({ secret: &quot;password&quot;,&amp;nbsp;&lt;/span&gt;&lt;br /&gt;
&lt;span style=&quot;font-family: &#39;Courier New&#39;, Courier, monospace;&quot;&gt;&amp;nbsp; &amp;nbsp; &amp;nbsp; &amp;nbsp; &amp;nbsp; &amp;nbsp; &amp;nbsp; &amp;nbsp; &amp;nbsp; &amp;nbsp; &amp;nbsp; &amp;nbsp; &amp;nbsp; &amp;nbsp;store: new RedisStore({&lt;/span&gt;&lt;br /&gt;
&lt;span style=&quot;font-family: &#39;Courier New&#39;, Courier, monospace;&quot;&gt;&amp;nbsp; &amp;nbsp; &amp;nbsp; &amp;nbsp; &amp;nbsp; &amp;nbsp; &amp;nbsp; &amp;nbsp; &amp;nbsp; &amp;nbsp; &amp;nbsp; &amp;nbsp; &amp;nbsp; &amp;nbsp; &amp;nbsp; &amp;nbsp; &amp;nbsp; &amp;nbsp; &amp;nbsp; &amp;nbsp; host: redisUrl.hostname,&lt;/span&gt;&lt;br /&gt;
&lt;span style=&quot;font-family: &#39;Courier New&#39;, Courier, monospace;&quot;&gt;&amp;nbsp; &amp;nbsp; &amp;nbsp; &amp;nbsp; &amp;nbsp; &amp;nbsp; &amp;nbsp; &amp;nbsp; &amp;nbsp; &amp;nbsp; &amp;nbsp; &amp;nbsp; &amp;nbsp; &amp;nbsp; &amp;nbsp; &amp;nbsp; &amp;nbsp; &amp;nbsp; &amp;nbsp; &amp;nbsp; port: redisUrl.port,&lt;/span&gt;&lt;br /&gt;
&lt;span style=&quot;font-family: &#39;Courier New&#39;, Courier, monospace;&quot;&gt;&amp;nbsp; &amp;nbsp; &amp;nbsp; &amp;nbsp; &amp;nbsp; &amp;nbsp; &amp;nbsp; &amp;nbsp; &amp;nbsp; &amp;nbsp; &amp;nbsp; &amp;nbsp; &amp;nbsp; &amp;nbsp; &amp;nbsp; &amp;nbsp; &amp;nbsp; &amp;nbsp; &amp;nbsp; &amp;nbsp; db: redisAuth[0],&lt;/span&gt;&lt;br /&gt;
&lt;span style=&quot;font-family: &#39;Courier New&#39;, Courier, monospace;&quot;&gt;&amp;nbsp; &amp;nbsp; &amp;nbsp; &amp;nbsp; &amp;nbsp; &amp;nbsp; &amp;nbsp; &amp;nbsp; &amp;nbsp; &amp;nbsp; &amp;nbsp; &amp;nbsp; &amp;nbsp; &amp;nbsp; &amp;nbsp; &amp;nbsp; &amp;nbsp; &amp;nbsp; &amp;nbsp; &amp;nbsp; pass: redisAuth[1]&lt;/span&gt;&lt;br /&gt;
&lt;span style=&quot;font-family: &#39;Courier New&#39;, Courier, monospace;&quot;&gt;&amp;nbsp; &amp;nbsp; &amp;nbsp; &amp;nbsp; &amp;nbsp; &amp;nbsp; &amp;nbsp; &amp;nbsp; &amp;nbsp; &amp;nbsp; &amp;nbsp; &amp;nbsp; &amp;nbsp; &amp;nbsp; &amp;nbsp; &amp;nbsp; &amp;nbsp; &amp;nbsp; &amp;nbsp; }) &amp;nbsp;&lt;/span&gt;&lt;br /&gt;
&lt;span style=&quot;font-family: &#39;Courier New&#39;, Courier, monospace;&quot;&gt;&amp;nbsp; &amp;nbsp; &amp;nbsp; &amp;nbsp; &amp;nbsp;}));&lt;/span&gt;&lt;br /&gt;
&lt;span style=&quot;font-family: &#39;Courier New&#39;, Courier, monospace;&quot;&gt;});&lt;/span&gt;&lt;br /&gt;
&lt;br /&gt;
Node.js and Connect-Redis will do the rest for you.&lt;br /&gt;
&lt;br /&gt;
The key will be the session id for the user with the value being a JSON serialised object of req.session.&lt;br /&gt;
&lt;br /&gt;</content><link rel='replies' type='application/atom+xml' href='http://blog.benhall.me.uk/feeds/6167590555739568321/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment/fullpage/post/21967381/6167590555739568321' title='1 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/21967381/posts/default/6167590555739568321'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/21967381/posts/default/6167590555739568321'/><link rel='alternate' type='text/html' href='http://blog.benhall.me.uk/2012/01/using-redis-and-redistogo-to-store.html' title='Using Redis and RedisToGo to store Node.js sessions on Heroku'/><author><name>Ben Hall</name><uri>http://www.blogger.com/profile/17734933641904484310</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='23' height='32' src='//blogger.googleusercontent.com/img/b/R29vZ2xl/AVvXsEiAHZKs2vYlTA1W58oZ3_laZ-JNsUCxXJj__UyIx7TgHEw6DD9nNDr5ML4vvTpu7HbXx0Q5FIWAXyJ2xRsiX97Iu12TNYdSZuMywoqD7Khsbz936TzlIJOBTkDINgB1iYc/s220/n792665715_5219640_7493.jpg'/></author><thr:total>1</thr:total></entry><entry><id>tag:blogger.com,1999:blog-21967381.post-8720353342311179063</id><published>2012-01-27T09:00:00.000+00:00</published><updated>2012-01-27T09:00:04.129+00:00</updated><category scheme="http://www.blogger.com/atom/ns#" term="commands"/><category scheme="http://www.blogger.com/atom/ns#" term="sed"/><title type='text'>In place editing of a file with sed</title><content type='html'>When writing a file modification script I find it annoying (read: boring) to write the logic of saving the file under a different name, moving to override original and then cleaning up. This is what I recently had to do and instead decided to look around at what other options were available, one of which was sed.&lt;br /&gt;
&lt;br /&gt;
The following command will replace the word testdomain with proddomain. &lt;br /&gt;
&lt;br /&gt;
&lt;span style=&quot;font-family: &#39;Courier New&#39;, Courier, monospace;&quot;&gt;$ echo &#39;www.testdomain.com&#39; &amp;gt; test.txt&lt;/span&gt;&lt;br /&gt;
&lt;span style=&quot;font-family: &#39;Courier New&#39;, Courier, monospace;&quot;&gt;$ cat test.txt&amp;nbsp;&lt;/span&gt;&lt;br /&gt;
&lt;span style=&quot;font-family: &#39;Courier New&#39;, Courier, monospace;&quot;&gt;www.testdomain.com
&lt;b&gt;&amp;nbsp;&lt;/b&gt;&lt;/span&gt;&lt;br /&gt;
&lt;b&gt;&lt;span style=&quot;font-family: &#39;Courier New&#39;, Courier, monospace;&quot;&gt;$ sed -i &#39;&#39; s/testdomain/proddomain/ test.txt&lt;/span&gt;&lt;/b&gt;&lt;br /&gt;
&lt;span style=&quot;font-family: &#39;Courier New&#39;, Courier, monospace;&quot;&gt;$ cat test.txt&lt;/span&gt;&lt;br /&gt;
&lt;span style=&quot;font-family: &#39;Courier New&#39;, Courier, monospace;&quot;&gt;www.proddomain.com &lt;/span&gt;&lt;br /&gt;
&lt;br /&gt;
The key to how this works is the -i &#39;&#39; argument of the sed command. -i specifies the file extension, by passing an empty string it uses the same file.</content><link rel='replies' type='application/atom+xml' href='http://blog.benhall.me.uk/feeds/8720353342311179063/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment/fullpage/post/21967381/8720353342311179063' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/21967381/posts/default/8720353342311179063'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/21967381/posts/default/8720353342311179063'/><link rel='alternate' type='text/html' href='http://blog.benhall.me.uk/2012/01/in-place-editing-of-file-with-sed.html' title='In place editing of a file with sed'/><author><name>Ben Hall</name><uri>http://www.blogger.com/profile/17734933641904484310</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='23' height='32' src='//blogger.googleusercontent.com/img/b/R29vZ2xl/AVvXsEiAHZKs2vYlTA1W58oZ3_laZ-JNsUCxXJj__UyIx7TgHEw6DD9nNDr5ML4vvTpu7HbXx0Q5FIWAXyJ2xRsiX97Iu12TNYdSZuMywoqD7Khsbz936TzlIJOBTkDINgB1iYc/s220/n792665715_5219640_7493.jpg'/></author><thr:total>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-21967381.post-6594910768710756449</id><published>2012-01-26T14:43:00.002+00:00</published><updated>2012-01-26T14:43:22.948+00:00</updated><category scheme="http://www.blogger.com/atom/ns#" term="nodejs"/><title type='text'>Getting node-compress to work on Node 0.6</title><content type='html'>I have a lot of respect for Node, but sometimes certain npm packages become out of sync with the latest version and break. Today, that npm package was node-compress.&lt;br /&gt;
&lt;br /&gt;
While the package looked to build, when attempting to require the module it would error.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&lt;span style=&quot;font-family: &#39;Courier New&#39;, Courier, monospace;&quot;&gt;$ node&lt;/span&gt;&lt;br /&gt;
&lt;span style=&quot;font-family: &#39;Courier New&#39;, Courier, monospace;&quot;&gt;&amp;gt; var c = require(&#39;compress&#39;)&lt;/span&gt;&lt;br /&gt;
&lt;span style=&quot;font-family: &#39;Courier New&#39;, Courier, monospace;&quot;&gt;Error: Cannot find module &#39;compress&#39;&lt;/span&gt;&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
After a quick look around on GitHub I found a fork with the fix&amp;nbsp;&lt;a href=&quot;https://github.com/elliotttf/node-compress/&quot;&gt;https://github.com/elliotttf/node-compress/&lt;/a&gt;&lt;br /&gt;
&lt;br /&gt;
In your package.json, simply reference the tarball, clean out the node_modules directory, install and everything should work again.&lt;br /&gt;
&lt;br /&gt;
&lt;span style=&quot;font-family: &#39;Courier New&#39;, Courier, monospace;&quot;&gt;Package.json&lt;/span&gt;&lt;br /&gt;
&lt;br /&gt;
&lt;span style=&quot;font-family: &#39;Courier New&#39;, Courier, monospace;&quot;&gt;&amp;nbsp; &amp;nbsp; , &quot;compress&quot;:&quot;https://github.com/elliotttf/node-compress/tarball/1edaa48bf33f7c836f1e275691e1d8645f0a71c3&quot;&lt;/span&gt;&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;</content><link rel='replies' type='application/atom+xml' href='http://blog.benhall.me.uk/feeds/6594910768710756449/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment/fullpage/post/21967381/6594910768710756449' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/21967381/posts/default/6594910768710756449'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/21967381/posts/default/6594910768710756449'/><link rel='alternate' type='text/html' href='http://blog.benhall.me.uk/2012/01/getting-node-compress-to-work-on-node.html' title='Getting node-compress to work on Node 0.6'/><author><name>Ben Hall</name><uri>http://www.blogger.com/profile/17734933641904484310</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='23' height='32' src='//blogger.googleusercontent.com/img/b/R29vZ2xl/AVvXsEiAHZKs2vYlTA1W58oZ3_laZ-JNsUCxXJj__UyIx7TgHEw6DD9nNDr5ML4vvTpu7HbXx0Q5FIWAXyJ2xRsiX97Iu12TNYdSZuMywoqD7Khsbz936TzlIJOBTkDINgB1iYc/s220/n792665715_5219640_7493.jpg'/></author><thr:total>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-21967381.post-1299516944614739481</id><published>2012-01-26T12:41:00.002+00:00</published><updated>2012-01-26T12:41:23.629+00:00</updated><category scheme="http://www.blogger.com/atom/ns#" term="Heroku"/><category scheme="http://www.blogger.com/atom/ns#" term="Mono"/><title type='text'>Video of How To Deploy a .NET App with Mono on Heroku</title><content type='html'>&lt;span class=&quot;job-title&quot; style=&quot;background-color: rgba(255, 255, 255, 0.917969); color: #404040; font-family: Arial; font-size: 13px; line-height: 15px;&quot;&gt;Wow. Chris Kemp (Advance technical solutions team&lt;/span&gt;&lt;span style=&quot;background-color: rgba(255, 255, 255, 0.917969); color: #404040; font-family: Arial; font-size: 13px; line-height: 15px;&quot;&gt;&amp;nbsp;at&amp;nbsp;&lt;/span&gt;&lt;span class=&quot;company&quot; style=&quot;background-color: rgba(255, 255, 255, 0.917969); color: #404040; font-family: Arial; font-size: 13px; line-height: 15px;&quot;&gt;&lt;a href=&quot;http://salesforce.com/&quot; target=&quot;_blank&quot;&gt;Salesforce.com&lt;/a&gt;) has create a great short video based on my blog post about &lt;b&gt;&lt;a href=&quot;http://blog.benhall.me.uk/2012/01/how-to-deploy-mono-projects-to-heroku.html&quot; target=&quot;_blank&quot;&gt;How To Deploy a .NET App with Mono on Heroku&lt;/a&gt;&lt;/b&gt;. A huge thank you!&lt;/span&gt;&lt;br /&gt;
&lt;br /&gt;
&lt;iframe allowfullscreen=&quot;&quot; frameborder=&quot;0&quot; height=&quot;360&quot; src=&quot;http://www.youtube.com/embed/LkdiTzgqqsk?rel=0&quot; width=&quot;640&quot;&gt;&lt;/iframe&gt;&lt;br /&gt;
&lt;br /&gt;
Link:&amp;nbsp;&lt;a href=&quot;http://www.youtube.com/watch?v=LkdiTzgqqsk&amp;amp;hd;=1&quot; target=&quot;_blank&quot;&gt;http://www.youtube.com/watch?v=LkdiTzgqqsk&amp;amp;hd;=1&lt;/a&gt;&lt;br /&gt;
&lt;br /&gt;</content><link rel='replies' type='application/atom+xml' href='http://blog.benhall.me.uk/feeds/1299516944614739481/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment/fullpage/post/21967381/1299516944614739481' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/21967381/posts/default/1299516944614739481'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/21967381/posts/default/1299516944614739481'/><link rel='alternate' type='text/html' href='http://blog.benhall.me.uk/2012/01/video-of-how-to-deploy-net-app-with.html' title='Video of How To Deploy a .NET App with Mono on Heroku'/><author><name>Ben Hall</name><uri>http://www.blogger.com/profile/17734933641904484310</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='23' height='32' src='//blogger.googleusercontent.com/img/b/R29vZ2xl/AVvXsEiAHZKs2vYlTA1W58oZ3_laZ-JNsUCxXJj__UyIx7TgHEw6DD9nNDr5ML4vvTpu7HbXx0Q5FIWAXyJ2xRsiX97Iu12TNYdSZuMywoqD7Khsbz936TzlIJOBTkDINgB1iYc/s220/n792665715_5219640_7493.jpg'/></author><media:thumbnail xmlns:media="http://search.yahoo.com/mrss/" url="https://img.youtube.com/vi/LkdiTzgqqsk/default.jpg" height="72" width="72"/><thr:total>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-21967381.post-3040100666029375781</id><published>2012-01-25T08:30:00.000+00:00</published><updated>2012-01-25T08:30:01.046+00:00</updated><category scheme="http://www.blogger.com/atom/ns#" term="Google Analytics"/><category scheme="http://www.blogger.com/atom/ns#" term="maydayhq"/><title type='text'>Help us by answering a questionnaire on Google Analytics</title><content type='html'>&lt;div&gt;
To help with development of &lt;a href=&quot;http://www.maydayhq.com/&quot; target=&quot;_blank&quot;&gt;Mayday&lt;/a&gt; we are asking people to fill out a questionnaire about how they use Google Analytics. If you use Google Analytics and have a moment to fill out the questionnaire then we would be most grateful.&lt;/div&gt;
&lt;div&gt;
&lt;br /&gt;&lt;/div&gt;
&lt;div&gt;
&lt;a href=&quot;https://docs.google.com/a/meerkatalyst.com/spreadsheet/viewform?hl=en_GB&amp;amp;formkey=dFlzVzRzX2k5d1FUb0ZYSkp1REZHR2c6MQ#gid=0&quot; target=&quot;_blank&quot;&gt;Visit our Google Analytics Questionnaire&lt;/a&gt;&amp;nbsp;&lt;/div&gt;
&lt;div&gt;
&lt;br /&gt;&lt;/div&gt;
&lt;div&gt;
Thank you.&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://blog.benhall.me.uk/feeds/3040100666029375781/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment/fullpage/post/21967381/3040100666029375781' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/21967381/posts/default/3040100666029375781'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/21967381/posts/default/3040100666029375781'/><link rel='alternate' type='text/html' href='http://blog.benhall.me.uk/2012/01/help-us-by-answering-questionnaire-on.html' title='Help us by answering a questionnaire on Google Analytics'/><author><name>Ben Hall</name><uri>http://www.blogger.com/profile/17734933641904484310</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='23' height='32' src='//blogger.googleusercontent.com/img/b/R29vZ2xl/AVvXsEiAHZKs2vYlTA1W58oZ3_laZ-JNsUCxXJj__UyIx7TgHEw6DD9nNDr5ML4vvTpu7HbXx0Q5FIWAXyJ2xRsiX97Iu12TNYdSZuMywoqD7Khsbz936TzlIJOBTkDINgB1iYc/s220/n792665715_5219640_7493.jpg'/></author><thr:total>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-21967381.post-3825299981707315813</id><published>2012-01-24T08:00:00.000+00:00</published><updated>2012-01-24T16:24:51.561+00:00</updated><category scheme="http://www.blogger.com/atom/ns#" term="ICanHazJS"/><category scheme="http://www.blogger.com/atom/ns#" term="Javascript"/><category scheme="http://www.blogger.com/atom/ns#" term="jQuery"/><title type='text'>A JavaScript equivalent to Ruby&#39;s respond_to?</title><content type='html'>&lt;br /&gt;
While working on the new version of &lt;a href=&quot;http://www.maydayhq.com/&quot;&gt;Mayday&lt;/a&gt;, I wanted to show a message if no data was returned from Google Analytics. To add to the complexity, I wanted to be able to override the default message on a per page basis.&lt;br /&gt;
&lt;br /&gt;
I&#39;m already using the&amp;nbsp;&lt;a href=&quot;http://icanhazjs.com/&quot;&gt;ICanHazJS&lt;/a&gt;&amp;nbsp;client-side&amp;nbsp;tempting&amp;nbsp;engine&amp;nbsp;which has a method for each template block on a page. However, if the page doesn&#39;t have the block then the method won&#39;t exist and an error will be thrown.&lt;br /&gt;
&lt;br /&gt;
What I needed was functionality similar to Ruby&#39;s respond_to. With this method I can ask the object if it will respond to the method call. For example: &lt;br /&gt;
&lt;br /&gt;
&lt;span style=&quot;font-family: &#39;Courier New&#39;, Courier, monospace;&quot;&gt;Object.respond_to? &#39;test&#39; #=&amp;gt; false&lt;/span&gt;&lt;br /&gt;
&lt;span style=&quot;font-family: &#39;Courier New&#39;, Courier, monospace;&quot;&gt;Object.respond_to? &#39;to_s&#39; #=&amp;gt; true&lt;/span&gt;&lt;br /&gt;
&lt;br /&gt;
Luckily this is just as easy to do in JavaScript using &#39;in&#39;&lt;br /&gt;
&lt;br /&gt;
&lt;span style=&quot;font-family: &#39;Courier New&#39;, Courier, monospace;&quot;&gt;&amp;gt; &#39;test&#39; in Object&lt;/span&gt;&lt;br /&gt;
&lt;span style=&quot;font-family: &#39;Courier New&#39;, Courier, monospace;&quot;&gt;false&lt;/span&gt;&lt;br /&gt;
&lt;span style=&quot;font-family: &#39;Courier New&#39;, Courier, monospace;&quot;&gt;&amp;gt; &#39;toString&#39; in Object&lt;/span&gt;&lt;br /&gt;
&lt;span style=&quot;font-family: &#39;Courier New&#39;, Courier, monospace;&quot;&gt;true&lt;/span&gt;&lt;br /&gt;
&lt;br /&gt;
This allowed me to write the following:&lt;br /&gt;
&lt;br /&gt;
&lt;span style=&quot;font-family: &#39;Courier New&#39;, Courier, monospace;&quot;&gt;var e = $(&#39;#data&#39;)&lt;/span&gt;&lt;br /&gt;
&lt;span style=&quot;font-family: &#39;Courier New&#39;, Courier, monospace;&quot;&gt;if(&#39;nodata&#39; in ich)&lt;/span&gt;&lt;br /&gt;
&lt;span style=&quot;font-family: &#39;Courier New&#39;, Courier, monospace;&quot;&gt;&amp;nbsp; &amp;nbsp;e.append(ich.nodata());&lt;/span&gt;&lt;br /&gt;
&lt;span style=&quot;font-family: &#39;Courier New&#39;, Courier, monospace;&quot;&gt;else&lt;/span&gt;&lt;br /&gt;
&lt;span style=&quot;font-family: &#39;Courier New&#39;, Courier, monospace;&quot;&gt;&amp;nbsp; &amp;nbsp;e.append(&#39;No Data Found&#39;);&lt;br /&gt;
&lt;/span&gt;&lt;br /&gt;
&lt;span style=&quot;font-family: inherit;&quot;&gt;&lt;br /&gt;
&lt;/span&gt;&lt;br /&gt;
&lt;span style=&quot;font-family: inherit;&quot;&gt;If a nodata ICanHaz template block appears on the page then it will be rendered, otherwise it will fall back to the default. Problem solved.&lt;/span&gt;&lt;br /&gt;
&lt;span style=&quot;font-family: inherit;&quot;&gt;&lt;br /&gt;
&lt;/span&gt;&lt;br /&gt;
&lt;span style=&quot;font-family: inherit;&quot;&gt;&lt;b&gt;Update:&lt;/b&gt;&amp;nbsp;&lt;/span&gt;&lt;br /&gt;
&lt;span style=&quot;font-family: inherit;&quot;&gt;&lt;br /&gt;
&lt;/span&gt;&lt;br /&gt;
&lt;span style=&quot;font-family: inherit;&quot;&gt;Problem almost solved. As pointed out on&amp;nbsp;&lt;a href=&quot;http://twitter.com/ben_hall&quot; target=&quot;_blank&quot;&gt;Twitter&lt;/a&gt;&amp;nbsp;by&amp;nbsp;&lt;/span&gt;&lt;a href=&quot;https://twitter.com/#!/nmosafi&quot;&gt;@nmosafi&lt;/a&gt;&amp;nbsp;and &lt;a href=&quot;https://twitter.com/#!/theprogrammer&quot; target=&quot;_blank&quot;&gt;@theprogrammer&lt;/a&gt;&lt;span style=&quot;font-family: inherit;&quot;&gt;, just using &#39;in&#39; along is not enough. &amp;nbsp;For example:&lt;/span&gt;&lt;br /&gt;
&lt;br /&gt;
&lt;span style=&quot;font-family: &#39;Courier New&#39;, Courier, monospace;&quot;&gt;&amp;gt; Object.test = &quot;test&quot;&lt;/span&gt;&lt;br /&gt;
&lt;span style=&quot;font-family: &#39;Courier New&#39;, Courier, monospace;&quot;&gt;&quot;test&quot;&lt;/span&gt;&lt;br /&gt;
&lt;span style=&quot;font-family: &#39;Courier New&#39;, Courier, monospace;&quot;&gt;&amp;gt; &#39;test&#39; in Object&lt;/span&gt;&lt;br /&gt;
&lt;span style=&quot;font-family: &#39;Courier New&#39;, Courier, monospace;&quot;&gt;true&lt;/span&gt;&lt;br /&gt;
&lt;span style=&quot;font-family: &#39;Courier New&#39;, Courier, monospace;&quot;&gt;&amp;gt; Object.test()&lt;/span&gt;&lt;br /&gt;
&lt;span style=&quot;font-family: &#39;Courier New&#39;, Courier, monospace;&quot;&gt;TypeError: Property &#39;test&#39; of object function Object() { [native code] } is not a function&lt;/span&gt;&lt;br /&gt;
&lt;br /&gt;
&lt;span style=&quot;font-family: &#39;Courier New&#39;, Courier, monospace;&quot;&gt;&lt;br /&gt;&lt;/span&gt;&lt;br /&gt;
&lt;span style=&quot;font-family: inherit;&quot;&gt;What you need to do is ensure that the property is also a function. Something I had assumed previously.&lt;/span&gt;&lt;br /&gt;
&lt;span style=&quot;font-family: inherit;&quot;&gt;&lt;br /&gt;&lt;/span&gt;&lt;br /&gt;
&lt;span style=&quot;font-family: &#39;Courier New&#39;, Courier, monospace;&quot;&gt;&amp;gt; &#39;test&#39; in Object &amp;amp;&amp;amp; typeof(Object.test) == &quot;function&quot;&lt;/span&gt;&lt;br /&gt;
&lt;span style=&quot;font-family: &#39;Courier New&#39;, Courier, monospace;&quot;&gt;false&lt;/span&gt;&lt;br /&gt;
&lt;br /&gt;
&lt;span style=&quot;font-family: &#39;Courier New&#39;, Courier, monospace;&quot;&gt;&amp;gt; &#39;toString&#39; in Object &amp;amp;&amp;amp; typeof(Object.toString) == &quot;function&quot;&lt;/span&gt;&lt;br /&gt;
&lt;span style=&quot;font-family: &#39;Courier New&#39;, Courier, monospace;&quot;&gt;true&lt;/span&gt;&lt;br /&gt;
&lt;br /&gt;</content><link rel='replies' type='application/atom+xml' href='http://blog.benhall.me.uk/feeds/3825299981707315813/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment/fullpage/post/21967381/3825299981707315813' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/21967381/posts/default/3825299981707315813'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/21967381/posts/default/3825299981707315813'/><link rel='alternate' type='text/html' href='http://blog.benhall.me.uk/2012/01/javascript-equivalent-to-rubys.html' title='A JavaScript equivalent to Ruby&#39;s respond_to?'/><author><name>Ben Hall</name><uri>http://www.blogger.com/profile/17734933641904484310</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='23' height='32' src='//blogger.googleusercontent.com/img/b/R29vZ2xl/AVvXsEiAHZKs2vYlTA1W58oZ3_laZ-JNsUCxXJj__UyIx7TgHEw6DD9nNDr5ML4vvTpu7HbXx0Q5FIWAXyJ2xRsiX97Iu12TNYdSZuMywoqD7Khsbz936TzlIJOBTkDINgB1iYc/s220/n792665715_5219640_7493.jpg'/></author><thr:total>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-21967381.post-4747674645488979100</id><published>2012-01-23T10:30:00.000+00:00</published><updated>2012-01-23T14:07:34.286+00:00</updated><category scheme="http://www.blogger.com/atom/ns#" term="expressjs"/><category scheme="http://www.blogger.com/atom/ns#" term="nodejs"/><title type='text'>Remove X-Powered-By for Express and NodeJS</title><content type='html'>When responding to a web request it&#39;s common for servers to tell the client various bits of information. The one they enjoy most is some promotion around the name and version &quot;powering&quot; the site. Sadly, hackers also love this as it gives them more information for an attack vector.&lt;br /&gt;
&lt;br /&gt;
By default, ExpressJS with NodeJS will return a X-Powered-By header.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&lt;span style=&quot;font-family: &#39;Courier New&#39;, Courier, monospace;&quot;&gt;$ curl -I 0.0.0.0:3000/&lt;/span&gt;&lt;br /&gt;
&lt;span style=&quot;font-family: &#39;Courier New&#39;, Courier, monospace;&quot;&gt;HTTP/1.1 302 Moved Temporarily&lt;/span&gt;&lt;br /&gt;
&lt;span style=&quot;font-family: &#39;Courier New&#39;, Courier, monospace;&quot;&gt;X-Powered-By: Express&lt;/span&gt;&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
I wasn&#39;t&amp;nbsp;overly&amp;nbsp;impressed by this but it&#39;s easy to remove. In your application configuration, at the top, add a new middleware function which removes the header.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&lt;span style=&quot;font-family: &#39;Courier New&#39;, Courier, monospace;&quot;&gt;&amp;nbsp; app.configure(function(){&lt;/span&gt;&lt;br /&gt;
&lt;span style=&quot;font-family: &#39;Courier New&#39;, Courier, monospace;&quot;&gt;&amp;nbsp; &amp;nbsp; &amp;nbsp; app.use(function (req, res, next) {&lt;/span&gt;&lt;br /&gt;
&lt;span style=&quot;font-family: &#39;Courier New&#39;, Courier, monospace;&quot;&gt;&amp;nbsp; &amp;nbsp; &amp;nbsp; &amp;nbsp; res.removeHeader(&quot;X-Powered-By&quot;);&lt;/span&gt;&lt;br /&gt;
&lt;span style=&quot;font-family: &#39;Courier New&#39;, Courier, monospace;&quot;&gt;&amp;nbsp; &amp;nbsp; &amp;nbsp; &amp;nbsp; next();&lt;/span&gt;&lt;br /&gt;
&lt;span style=&quot;font-family: &#39;Courier New&#39;, Courier, monospace;&quot;&gt;&amp;nbsp; &amp;nbsp; &amp;nbsp; });&amp;nbsp;&lt;/span&gt;&lt;br /&gt;
&lt;span style=&quot;font-family: &#39;Courier New&#39;, Courier, monospace;&quot;&gt;&lt;br /&gt;&lt;/span&gt;&lt;br /&gt;
&lt;span style=&quot;font-family: &#39;Courier New&#39;, Courier, monospace;&quot;&gt;&amp;nbsp; &amp;nbsp; &amp;nbsp; app.set(&#39;views&#39;, __dirname + &#39;/views&#39;);&lt;/span&gt;&lt;br /&gt;
&lt;span style=&quot;font-family: &#39;Courier New&#39;, Courier, monospace;&quot;&gt;&amp;nbsp; &amp;nbsp; &amp;nbsp; app.set(&#39;view engine&#39;, &#39;jade&#39;);&lt;/span&gt;&lt;br /&gt;
&lt;span style=&quot;font-family: &#39;Courier New&#39;, Courier, monospace;&quot;&gt;&amp;nbsp; &amp;nbsp; &amp;nbsp; app.use(express.bodyParser());&lt;/span&gt;&lt;br /&gt;
&lt;span style=&quot;font-family: &#39;Courier New&#39;, Courier, monospace;&quot;&gt;&amp;nbsp; &amp;nbsp; &amp;nbsp; app.use(express.methodOverride());&lt;/span&gt;&lt;br /&gt;
&lt;span style=&quot;font-family: &#39;Courier New&#39;, Courier, monospace;&quot;&gt;&amp;nbsp; &amp;nbsp; &amp;nbsp; app.use(express.cookieParser());&lt;/span&gt;&lt;br /&gt;
&lt;span style=&quot;font-family: &#39;Courier New&#39;, Courier, monospace;&quot;&gt;&amp;nbsp; &amp;nbsp; &amp;nbsp; app.use(express.static(__dirname + &#39;/static&#39;));&lt;/span&gt;&lt;br /&gt;
&lt;span style=&quot;font-family: &#39;Courier New&#39;, Courier, monospace;&quot;&gt;&amp;nbsp; });&lt;/span&gt;&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
Simple.&lt;br /&gt;
&lt;br /&gt;</content><link rel='replies' type='application/atom+xml' href='http://blog.benhall.me.uk/feeds/4747674645488979100/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment/fullpage/post/21967381/4747674645488979100' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/21967381/posts/default/4747674645488979100'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/21967381/posts/default/4747674645488979100'/><link rel='alternate' type='text/html' href='http://blog.benhall.me.uk/2012/01/removed-x-powered-by-for-express-and.html' title='Remove X-Powered-By for Express and NodeJS'/><author><name>Ben Hall</name><uri>http://www.blogger.com/profile/17734933641904484310</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='23' height='32' src='//blogger.googleusercontent.com/img/b/R29vZ2xl/AVvXsEiAHZKs2vYlTA1W58oZ3_laZ-JNsUCxXJj__UyIx7TgHEw6DD9nNDr5ML4vvTpu7HbXx0Q5FIWAXyJ2xRsiX97Iu12TNYdSZuMywoqD7Khsbz936TzlIJOBTkDINgB1iYc/s220/n792665715_5219640_7493.jpg'/></author><thr:total>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-21967381.post-3908560382479804769</id><published>2012-01-21T18:55:00.003+00:00</published><updated>2012-01-21T18:56:14.884+00:00</updated><category scheme="http://www.blogger.com/atom/ns#" term="grep"/><category scheme="http://www.blogger.com/atom/ns#" term="nodejs"/><title type='text'>Finding out where that console.log output is coming from</title><content type='html'>While trying to solve a problem, we have all sometimes done a little console.log outputting to help us gain additional understanding. While it&#39;s far from the most effect way of debugging, it&#39;s more annoying when those statements appear in your production logs. That was my scenario today.&lt;br /&gt;
&lt;br /&gt;
Thankfully, with a simple grep command I was able to identified all of my &quot;debugging&quot; statements and the lines they occurred on.&lt;br /&gt;
&lt;br /&gt;
&lt;span style=&quot;font-family: &#39;Courier New&#39;, Courier, monospace;&quot;&gt;$ grep -nr console * | grep -v &quot;node_modules/*&quot; | grep -v &quot;static/&quot;&lt;/span&gt;&lt;br /&gt;
&lt;br /&gt;
&lt;span style=&quot;font-family: &#39;Courier New&#39;, Courier, monospace;&quot;&gt;endpoints/browser_stats.js:35: &amp;nbsp; &amp;nbsp; &amp;nbsp; &amp;nbsp;if(error) { console.log(error); }&lt;/span&gt;&lt;br /&gt;
&lt;span style=&quot;font-family: &#39;Courier New&#39;, Courier, monospace;&quot;&gt;endpoints/browser_stats.js:51: &amp;nbsp; &amp;nbsp; &amp;nbsp; &amp;nbsp;if(error) { console.log(error); }&lt;/span&gt;&lt;br /&gt;
&lt;span style=&quot;font-family: &#39;Courier New&#39;, Courier, monospace;&quot;&gt;endpoints/browser_stats.js:67: &amp;nbsp; &amp;nbsp; &amp;nbsp; &amp;nbsp;if(error) { console.log(error); }&lt;/span&gt;&lt;br /&gt;
&lt;span style=&quot;font-family: &#39;Courier New&#39;, Courier, monospace;&quot;&gt;endpoints/events.js:16: &amp;nbsp; &amp;nbsp;console.log(eventsUrl);&lt;/span&gt;&lt;br /&gt;
&lt;span style=&quot;font-family: &#39;Courier New&#39;, Courier, monospace;&quot;&gt;endpoints/events.js:17: &amp;nbsp; &amp;nbsp;console.log(hitsUrl);&lt;/span&gt;&lt;br /&gt;
&lt;span style=&quot;font-family: &#39;Courier New&#39;, Courier, monospace;&quot;&gt;endpoints/events.js:20: &amp;nbsp; &amp;nbsp; &amp;nbsp; &amp;nbsp;if(error) { console.log(error); }&lt;/span&gt;&lt;br /&gt;
&lt;span style=&quot;font-family: &#39;Courier New&#39;, Courier, monospace;&quot;&gt;endpoints/events.js:27: &amp;nbsp; &amp;nbsp; &amp;nbsp; &amp;nbsp; &amp;nbsp; &amp;nbsp;if(error) { console.log(error); }&lt;/span&gt;&lt;br /&gt;
&lt;span style=&quot;font-family: &#39;Courier New&#39;, Courier, monospace;&quot;&gt;passport.js:23: &amp;nbsp; &amp;nbsp; &amp;nbsp;console.log(&quot;Auth&quot;);&lt;/span&gt;&lt;br /&gt;
&lt;br /&gt;
In this case, I filtered out any matches from node_modules and static javascript files. Keep in mind that in some cases it&#39;s a node module causing the output.&lt;br /&gt;
&lt;br /&gt;
A simple command to help keep your production logs clean and readable.</content><link rel='replies' type='application/atom+xml' href='http://blog.benhall.me.uk/feeds/3908560382479804769/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment/fullpage/post/21967381/3908560382479804769' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/21967381/posts/default/3908560382479804769'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/21967381/posts/default/3908560382479804769'/><link rel='alternate' type='text/html' href='http://blog.benhall.me.uk/2012/01/finding-out-where-that-consolelog.html' title='Finding out where that console.log output is coming from'/><author><name>Ben Hall</name><uri>http://www.blogger.com/profile/17734933641904484310</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='23' height='32' src='//blogger.googleusercontent.com/img/b/R29vZ2xl/AVvXsEiAHZKs2vYlTA1W58oZ3_laZ-JNsUCxXJj__UyIx7TgHEw6DD9nNDr5ML4vvTpu7HbXx0Q5FIWAXyJ2xRsiX97Iu12TNYdSZuMywoqD7Khsbz936TzlIJOBTkDINgB1iYc/s220/n792665715_5219640_7493.jpg'/></author><thr:total>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-21967381.post-1454370090471583058</id><published>2012-01-20T09:30:00.000+00:00</published><updated>2012-01-20T13:05:17.936+00:00</updated><category scheme="http://www.blogger.com/atom/ns#" term="Javascript"/><title type='text'>Javascript WTF: The Date object</title><content type='html'>&lt;br /&gt;
Almost every time I have to deal with the Date object in Javascript I always hit the same WTF.&lt;br /&gt;
&lt;br /&gt;
The &lt;a href=&quot;https://developer.mozilla.org/en/JavaScript/Reference/Global_Objects/Date&quot; target=&quot;_blank&quot;&gt;documentation&lt;/a&gt; is clear but the API has some strange aspects that personally I don&#39;t think&amp;nbsp;reflect the real world and how we naturally handle dates.&lt;br /&gt;
&lt;br /&gt;
For example:&lt;br /&gt;
&amp;nbsp; &amp;nbsp; &amp;nbsp;&amp;nbsp;&lt;span style=&quot;font-family: &#39;Courier New&#39;, Courier, monospace;&quot;&gt;getDay()&lt;/span&gt; returns the day of the week (0-6) leaving &lt;span style=&quot;font-family: &#39;Courier New&#39;, Courier, monospace;&quot;&gt;getDate()&lt;/span&gt; to return 1-31. Personally, I would have imagined getDate() to return DMY with &lt;span style=&quot;font-family: &#39;Courier New&#39;, Courier, monospace;&quot;&gt;getDay()&lt;/span&gt; returning 1-31. &lt;br /&gt;
&amp;nbsp; &amp;nbsp; &amp;nbsp;&amp;nbsp;&lt;span style=&quot;font-family: &#39;Courier New&#39;, Courier, monospace;&quot;&gt;getMonth()&lt;/span&gt; returns 0-11.&amp;nbsp; Classic computer science with starting the count at 0 while the Gregorian calendar is 1-12. This is also inconsistent with &lt;span style=&quot;font-family: &#39;Courier New&#39;, Courier, monospace;&quot;&gt;getDate()&lt;/span&gt; which starts at 1. &lt;br /&gt;
&amp;nbsp; &amp;nbsp; &amp;nbsp; &lt;span style=&quot;font-family: &#39;Courier New&#39;, Courier, monospace;&quot;&gt;getYear()&lt;/span&gt; returns the year (usually 2-3 digits). For example, 2012 is 
obviously 112. You need to use &lt;span style=&quot;font-family: &#39;Courier New&#39;, Courier, monospace;&quot;&gt;getFullYear()&lt;/span&gt; to return 2012. The logic 
about how the method came to 112 is found at &lt;a href=&quot;https://developer.mozilla.org/en/JavaScript/Reference/Global_Objects/Date/getYear&quot;&gt;https://developer.mozilla.org/en/JavaScript/Reference/Global_Objects/Date/getYear&lt;/a&gt;&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
JavaScript 1.0 - we love you and you have left an impact in many ways.</content><link rel='replies' type='application/atom+xml' href='http://blog.benhall.me.uk/feeds/1454370090471583058/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment/fullpage/post/21967381/1454370090471583058' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/21967381/posts/default/1454370090471583058'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/21967381/posts/default/1454370090471583058'/><link rel='alternate' type='text/html' href='http://blog.benhall.me.uk/2012/01/javascript-wtf-date-object.html' title='Javascript WTF: The Date object'/><author><name>Ben Hall</name><uri>http://www.blogger.com/profile/17734933641904484310</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='23' height='32' src='//blogger.googleusercontent.com/img/b/R29vZ2xl/AVvXsEiAHZKs2vYlTA1W58oZ3_laZ-JNsUCxXJj__UyIx7TgHEw6DD9nNDr5ML4vvTpu7HbXx0Q5FIWAXyJ2xRsiX97Iu12TNYdSZuMywoqD7Khsbz936TzlIJOBTkDINgB1iYc/s220/n792665715_5219640_7493.jpg'/></author><thr:total>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-21967381.post-1834382741126236120</id><published>2012-01-19T18:02:00.000+00:00</published><updated>2012-01-20T16:32:52.813+00:00</updated><category scheme="http://www.blogger.com/atom/ns#" term="Javascript"/><category scheme="http://www.blogger.com/atom/ns#" term="MDN"/><category scheme="http://www.blogger.com/atom/ns#" term="PromoteJS"/><title type='text'>Setting a cookie in Javascript shouldn&#39;t be THAT difficult</title><content type='html'>With Javascript becoming increasingly popular, I&#39;m still shocked at how bad the online documentation and examples are.&amp;nbsp; Let&#39;s take the search phase &quot;&lt;b&gt;setting a cookie in javascript&lt;/b&gt;&quot;, a fairly common problem which I always forget the correct syntax for.&lt;br /&gt;
&lt;br /&gt;
The first four results are as follows:&lt;br /&gt;
http://www.w3schools.com/js/js_cookies.asp&lt;br /&gt;
http://www.quirksmode.org/js/cookies.html&lt;br /&gt;
http://techpatterns.com/downloads/javascript_cookies.php&lt;br /&gt;
http://www.javascripter.net/faq/settinga.htm&lt;br /&gt;
&lt;br /&gt;
Sorry to the original authors, but each one of them &lt;i&gt;IS AWFUL&lt;/i&gt;!&lt;br /&gt;
&lt;br /&gt;
Let&#39;s take W3Schools as an example. It defines a variable called ARRCookies&lt;code&gt;&lt;/code&gt; are could be for Pirate Cookies (via &lt;a href=&quot;http://twitter.com/blowdart&quot; target=&quot;_blank&quot;&gt;@Blowdart&lt;/a&gt;) or ARRay (via &lt;a href=&quot;https://twitter.com/#%21/AndrewVos&quot; target=&quot;_blank&quot;&gt;@AndrewVos&lt;/a&gt;) - both of which are great examples of creating Clean Code. To make matters even worse, this example has spread like a virus with Google returning 288,000 results and GitHub returning 398.&lt;br /&gt;
&lt;br /&gt;
The best link which describes handling cookies, and generally any Javascript documentation, can be found on the &lt;b&gt;Mozilla Developer Network (MDN)&lt;/b&gt;. &lt;br /&gt;
&lt;br /&gt;
&lt;a href=&quot;https://developer.mozilla.org/en/DOM/document.cookie&quot; target=&quot;_blank&quot;&gt;https://developer.mozilla.org/en/DOM/document.cookie&lt;/a&gt;&lt;br /&gt;
&lt;br /&gt;
While I&#39;m not an SEO expert, this looks to be light on SEO (Search Engine Optimisation) related to phases people search for. As a result the link was found in the lonely spot on page 3 which is should be number 1.&lt;br /&gt;
&lt;br /&gt;
Wouldn&#39;t it be great if MDN had SEO focused content to support the excellent reference material it already has available? The &lt;a href=&quot;http://blog.benhall.me.uk/2010/10/im-pirate-lets-make-change-promotejs.html&quot; target=&quot;_blank&quot;&gt;PromoteJS movement&lt;/a&gt; has made a start but I think it needs a kick-start.&lt;br /&gt;
&lt;br /&gt;
Who&#39;s with &lt;a href=&quot;http://twitter.com/ben_hall&quot; target=&quot;_blank&quot;&gt;me&lt;/a&gt;?&lt;br /&gt;
&lt;br /&gt;
&lt;b&gt;UPDATE (20/1/12):&lt;/b&gt;&lt;br /&gt;
&lt;br /&gt;
In a moment of great timing, the Mozilla WebDev team started a AMA (Ask Me Anything) thread on Reddit. I pointed out the above comments and had some great responses from the team.&lt;br /&gt;
&lt;br /&gt;
It turns out that MDN is a wiki so it&#39;s in the community (and my hands) to make a difference.&lt;br /&gt;
&lt;br /&gt;
You can read the comments here:&lt;br /&gt;
&lt;br /&gt;
&lt;a href=&quot;http://www.reddit.com/r/IAmA/comments/oonrg/iama_member_of_the_mozilla_webdev_team_ama/c3iup1b&quot;&gt;http://www.reddit.com/r/IAmA/comments/oonrg/iama_member_of_the_mozilla_webdev_team_ama/c3iup1b&lt;/a&gt;&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;</content><link rel='replies' type='application/atom+xml' href='http://blog.benhall.me.uk/feeds/1834382741126236120/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment/fullpage/post/21967381/1834382741126236120' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/21967381/posts/default/1834382741126236120'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/21967381/posts/default/1834382741126236120'/><link rel='alternate' type='text/html' href='http://blog.benhall.me.uk/2012/01/setting-cookie-in-javascript-shouldnt.html' title='Setting a cookie in Javascript shouldn&#39;t be THAT difficult'/><author><name>Ben Hall</name><uri>http://www.blogger.com/profile/17734933641904484310</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='23' height='32' src='//blogger.googleusercontent.com/img/b/R29vZ2xl/AVvXsEiAHZKs2vYlTA1W58oZ3_laZ-JNsUCxXJj__UyIx7TgHEw6DD9nNDr5ML4vvTpu7HbXx0Q5FIWAXyJ2xRsiX97Iu12TNYdSZuMywoqD7Khsbz936TzlIJOBTkDINgB1iYc/s220/n792665715_5219640_7493.jpg'/></author><thr:total>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-21967381.post-5423979164265586365</id><published>2012-01-11T16:48:00.000+00:00</published><updated>2012-01-11T16:53:57.065+00:00</updated><category scheme="http://www.blogger.com/atom/ns#" term="Heroku"/><category scheme="http://www.blogger.com/atom/ns#" term="Mono"/><title type='text'>How to deploy Mono projects with Heroku</title><content type='html'>Last week I &lt;a href=&quot;http://blog.benhall.me.uk/2012/01/experiment-deploying-c-mono-on-heroku.html&quot; target=&quot;_blank&quot;&gt;mentioned&lt;/a&gt; how I had successfully deployed &lt;a href=&quot;http://nancyfx.org/&quot; target=&quot;_blank&quot;&gt;Nancy&lt;/a&gt; / &lt;a href=&quot;http://www.mono-project.com/Main_Page&quot; target=&quot;_blank&quot;&gt;Mono&lt;/a&gt; (C# frameworks) onto &lt;a href=&quot;http://www.heroku.com/&quot; target=&quot;_blank&quot;&gt;Heroku&lt;/a&gt;.&amp;nbsp; This post covers how you can deploy your own Mono projects onto Heroku.&lt;br /&gt;
&lt;br /&gt;
As before, this approach is &lt;i&gt;completely unsupported&lt;/i&gt; by Heroku and I&#39;m not 100% sure if it&#39;s production ready. I would love to hear your experiences.&lt;br /&gt;
&lt;br /&gt;
&lt;b&gt;0) Prerequisites&amp;nbsp;&lt;/b&gt;&lt;br /&gt;
There are a few requirements before deploying a project.&lt;br /&gt;
&amp;nbsp;&amp;nbsp;&amp;nbsp; - The solution can compile using Mono on Linux (Ubuntu 10.04 - &lt;span class=&quot;st&quot;&gt;Lucid Lynx)&lt;/span&gt;.&amp;nbsp; &lt;br /&gt;
&amp;nbsp;&amp;nbsp;&amp;nbsp; - The launch application must be a self-hosted executable. &lt;br /&gt;
&amp;nbsp;&amp;nbsp;&amp;nbsp; - The self-hosted executable must stay alive and not exit. Example: &lt;a href=&quot;https://github.com/BenHall/nancy-demo-hosting-self/blob/master/src/Program.cs#L20-23&quot; target=&quot;_blank&quot;&gt;https://github.com/BenHall/nancy-demo-hosting-self/blob/master/src/Program.cs#L20-23&lt;/a&gt;&lt;br /&gt;
&lt;br /&gt;
&lt;b&gt;1) Update heroku gem&lt;/b&gt;&lt;br /&gt;
Before you continue, make sure your running the latest heroku gem as you need the buildpack option which is only supported in later versions. Thanks &lt;a href=&quot;https://twitter.com/#%21/andypike&quot; target=&quot;_blank&quot;&gt;Andy Pike&lt;/a&gt; for pointing this out.&lt;br /&gt;
&lt;br /&gt;
&lt;pre&gt;$ gem update heroku&lt;/pre&gt;&lt;br /&gt;
&lt;b&gt;2) Listening to Heroku requests&lt;/b&gt;&lt;br /&gt;
This is the only part which I&#39;m not too happy with. In order for Mono to accept Heroku requests, you need to bind the listener to the full hostname provided by Heroku - for example http://deep-moon-1452.herokuapp.com.&lt;br /&gt;
&lt;br /&gt;
The application also needs to listen on a particular port randomly defined by Heroku. This is provided via an environment variable.&amp;nbsp; &lt;br /&gt;
&lt;br /&gt;
Example:&lt;br /&gt;
&lt;a href=&quot;http://www.blogger.com/goog_671744702&quot;&gt;https:&lt;/a&gt;&lt;a href=&quot;https://github.com/BenHall/nancy-demo-hosting-self/blob/master/src/Program.cs#L12&quot; target=&quot;_blank&quot;&gt;//github.com/BenHall/nancy-demo-hosting-self/blob/master/src/Program.cs#L12&lt;/a&gt;&lt;br /&gt;
&lt;br /&gt;
Ironically this is the part which blocked me and after multiple combinations I was left with hard-coding the name as my last resort - see the commit &lt;a href=&quot;https://github.com/BenHall/nancy-demo-hosting-self/commit/4d9e07bed92559a53b1463c37e837045d59c3a9a&quot;&gt;https://github.com/BenHall/nancy-demo-hosting-self/commit/4d9e07bed92559a53b1463c37e837045d59c3a9a&lt;/a&gt;&lt;br /&gt;
&lt;br /&gt;
&lt;b&gt;3) How projects are built during deployment&lt;/b&gt;&lt;br /&gt;
Projects are built on Heroku during the git push process.&amp;nbsp; To find a solution to build, the command &quot;&lt;span style=&quot;font-family: &amp;quot;Courier New&amp;quot;,Courier,monospace;&quot;&gt;ls &lt;span class=&quot;nv&quot;&gt;$BUILD_DIR&lt;/span&gt;/*.sln | head -1&lt;/span&gt;&lt;span class=&quot;k&quot;&gt;&quot; is used. This will return the name of the first solution file found.&lt;/span&gt;&lt;br /&gt;
Once the name has been determined, xbuild is called with the output streamed back. If the build fails, the deployment is stopped.&lt;br /&gt;
&lt;br /&gt;
&lt;b&gt;4) How the application is launched - Procfile&lt;/b&gt;&lt;br /&gt;
Once the project has been built, the self-hosted executable needs to be executed via a &lt;a href=&quot;http://devcenter.heroku.com/articles/procfile&quot; target=&quot;_blank&quot;&gt;Procfile&lt;/a&gt;.&lt;br /&gt;
&lt;br /&gt;
An example can be found here:&lt;br /&gt;
&lt;a href=&quot;https://github.com/BenHall/nancy-demo-hosting-self/blob/master/Procfile&quot;&gt;https://github.com/BenHall/nancy-demo-hosting-self/blob/master/Procfile&lt;/a&gt;&lt;br /&gt;
&lt;br /&gt;
The  web property specifies the command used by Heroku. The  first part is  the path to mono which is defined in the buildpack and shouldn&#39;t be change. The second part is  the relative path to your compiled  executable.&lt;br /&gt;
&lt;br /&gt;
In the example I also defined a local  environment command allowing me to replicate the hosted environment  locally via &quot;foreman start local&quot;.&amp;nbsp; &lt;br /&gt;
&lt;br /&gt;
&lt;b&gt;5) Creating the Heroku environment - Cedar and buildpacks&lt;/b&gt;&lt;br /&gt;
When creating your Heroku application to host your project, it&#39;s important to specify the stack as cedar along with the buildpack for Mono. The buildpack defines the steps required to download Mono from my S3 account, configure the environment and build your solution.&lt;br /&gt;
&lt;br /&gt;
&lt;pre&gt;&lt;code&gt;$ heroku create --stack cedar --buildpack http://github.com/BenHall/heroku-buildpack-mono&amp;nbsp;&lt;/code&gt;&lt;/pre&gt;&lt;br /&gt;
Remember to change the hostname your exe listens on otherwise you&#39;ll received a Bad Request (Invalid Host) response.&lt;br /&gt;
&lt;br /&gt;
If you receive the error &quot;!Name must start with a letter and can only contain lowercase letters, numbers, and dashes&quot; then make sure your using the latest Heroku gem (currently 2.18.1). &lt;br /&gt;
&lt;br /&gt;
&lt;b&gt;6) Push&lt;/b&gt;&lt;br /&gt;
A simple push should now be all you need.&lt;br /&gt;
&lt;pre&gt;&lt;code&gt;$ git push heroku master&lt;/code&gt;&lt;/pre&gt;Done!&amp;nbsp; Technical details about how the buildpack works in a future post.&lt;br /&gt;
&lt;br /&gt;
Important links:&lt;br /&gt;
Buildpack:&amp;nbsp; &lt;a href=&quot;https://github.com/BenHall/heroku-buildpack-mono&quot;&gt;https://github.com/BenHall/heroku-buildpack-mono&lt;/a&gt;&lt;br /&gt;
Example: &lt;a href=&quot;https://github.com/BenHall/nancy-demo-hosting-self&quot;&gt;https://github.com/BenHall/nancy-demo-hosting-self&lt;/a&gt;&lt;br /&gt;
&lt;br /&gt;
&lt;b&gt;&lt;i&gt;tl;dr: The main steps are&lt;/i&gt;&lt;/b&gt;&lt;br /&gt;
0) &lt;code&gt; $ gem update heroku&lt;/code&gt; &lt;br /&gt;
1) &lt;code&gt; $ git clone &lt;a href=&quot;https://github.com/BenHall/nancy-demo-hosting-self&quot;&gt;https://github.com/BenHall/nancy-demo-hosting-self&lt;/a&gt;&lt;/code&gt;&lt;br /&gt;
2) &lt;code&gt; $ cd nancy-demo-hosting-self&lt;/code&gt;&lt;br /&gt;
3) &lt;code&gt; $ heroku create --stack cedar --buildpack http://github.com/BenHall/heroku-buildpack-mono&lt;/code&gt;&lt;br /&gt;
4) Replace&lt;span class=&quot;s&quot;&gt; deep-moon-1452&lt;/span&gt; in src/Program.cs to the application name created above&lt;br /&gt;
5) &lt;code&gt; $ git commit -am &quot;Changed application name&quot; &lt;/code&gt;&lt;br /&gt;
6) &lt;code&gt; $ git push heroku master&lt;/code&gt;&lt;br /&gt;
7) Tweet to say how amazing it is.&lt;br /&gt;
&lt;br /&gt;</content><link rel='replies' type='application/atom+xml' href='http://blog.benhall.me.uk/feeds/5423979164265586365/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment/fullpage/post/21967381/5423979164265586365' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/21967381/posts/default/5423979164265586365'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/21967381/posts/default/5423979164265586365'/><link rel='alternate' type='text/html' href='http://blog.benhall.me.uk/2012/01/how-to-deploy-mono-projects-to-heroku.html' title='How to deploy Mono projects with Heroku'/><author><name>Ben Hall</name><uri>http://www.blogger.com/profile/17734933641904484310</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='23' height='32' src='//blogger.googleusercontent.com/img/b/R29vZ2xl/AVvXsEiAHZKs2vYlTA1W58oZ3_laZ-JNsUCxXJj__UyIx7TgHEw6DD9nNDr5ML4vvTpu7HbXx0Q5FIWAXyJ2xRsiX97Iu12TNYdSZuMywoqD7Khsbz936TzlIJOBTkDINgB1iYc/s220/n792665715_5219640_7493.jpg'/></author><thr:total>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-21967381.post-1852698578104564876</id><published>2012-01-03T18:15:00.001+00:00</published><updated>2012-01-03T19:32:37.875+00:00</updated><title type='text'>Experiment: Deploying C# / Mono on Heroku</title><content type='html'>Over the past couple of days I&#39;ve been trying to get Mono running on top of &lt;a href=&quot;http://www.heroku.com/&quot; target=&quot;_blank&quot;&gt;Heroku&lt;/a&gt;.&lt;br /&gt;
&lt;br /&gt;
I&#39;m pleased to report that I have&amp;nbsp;&lt;b&gt;successfully &lt;/b&gt;deployed&lt;b&gt;&amp;nbsp;&lt;/b&gt;&lt;a href=&quot;http://www.nancyfx.org/&quot; target=&quot;_blank&quot;&gt;Nancy&lt;/a&gt; (a C# web framework)&amp;nbsp;on top of Heroku.&lt;br /&gt;
&lt;br /&gt;
It&#39;s far from a production ready solution and is &lt;i&gt;completely unsupported&lt;/i&gt;&amp;nbsp;by Heroku but it&#39;s an interesting experiment.&amp;nbsp;More technical details in future posts but here&#39;s some proof.&lt;br /&gt;
&lt;br /&gt;
Server response headers:&lt;br /&gt;
&lt;span style=&quot;font-family: &#39;Courier New&#39;, Courier, monospace;&quot;&gt;$ curl -i http://deep-moon-1452.herokuapp.com/&lt;/span&gt;&lt;br /&gt;
&lt;span style=&quot;font-family: &#39;Courier New&#39;, Courier, monospace;&quot;&gt;HTTP/1.1 200 OK&lt;/span&gt;&lt;br /&gt;
&lt;span style=&quot;font-family: &#39;Courier New&#39;, Courier, monospace;&quot;&gt;Content-Type: text/html&lt;/span&gt;&lt;br /&gt;
&lt;span style=&quot;font-family: &#39;Courier New&#39;, Courier, monospace;&quot;&gt;Date: Tue, 03 Jan 2012 16:33:02 GMT&lt;/span&gt;&lt;br /&gt;
&lt;span style=&quot;font-family: &#39;Courier New&#39;, Courier, monospace;&quot;&gt;Nancy-Version: 0.9.0.0&lt;/span&gt;&lt;br /&gt;
&lt;span style=&quot;font-family: &#39;Courier New&#39;, Courier, monospace;&quot;&gt;Server: Mono-HTTPAPI/1.0&lt;/span&gt;&lt;br /&gt;
&lt;br /&gt;
Screenshot:&lt;br /&gt;
&lt;div class=&quot;separator&quot; style=&quot;text-align: center;&quot;&gt;
&lt;a href=&quot;https://blogger.googleusercontent.com/img/b/R29vZ2xl/AVvXsEhipxK-uHdH6QAUy_nAtMr3TzU7alDv7L8D7SDYiH5-CUSnWBswlOf8LWHZagAVh5Nsrz7Ucobh-fPY5m3k_u4cLM0DdMhyM-seMEQGjYaOq0EzL614xkusDaSkfWAHRRNOpM4l/s1600/nancy_heroku_v1.png&quot; imageanchor=&quot;1&quot; style=&quot;clear: left; float: left; margin-bottom: 1em; margin-right: 1em;&quot;&gt;&lt;img border=&quot;0&quot; height=&quot;243&quot; src=&quot;https://blogger.googleusercontent.com/img/b/R29vZ2xl/AVvXsEhipxK-uHdH6QAUy_nAtMr3TzU7alDv7L8D7SDYiH5-CUSnWBswlOf8LWHZagAVh5Nsrz7Ucobh-fPY5m3k_u4cLM0DdMhyM-seMEQGjYaOq0EzL614xkusDaSkfWAHRRNOpM4l/s400/nancy_heroku_v1.png&quot; width=&quot;400&quot; /&gt;&lt;/a&gt;&lt;/div&gt;
&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
This is the output when you push your git repository to Heroku. The source code is built on Heroku.&lt;br /&gt;
&lt;br /&gt;
&lt;span style=&quot;font-family: &#39;Courier New&#39;, Courier, monospace;&quot;&gt;$ git push heroku master&lt;/span&gt;&lt;br /&gt;
&lt;span style=&quot;font-family: &#39;Courier New&#39;, Courier, monospace;&quot;&gt;Counting objects: 9, done.&lt;/span&gt;&lt;br /&gt;
&lt;span style=&quot;font-family: &#39;Courier New&#39;, Courier, monospace;&quot;&gt;Delta compression using up to 2 threads.&lt;/span&gt;&lt;br /&gt;
&lt;span style=&quot;font-family: &#39;Courier New&#39;, Courier, monospace;&quot;&gt;Compressing objects: 100% (4/4), done.&lt;/span&gt;&lt;br /&gt;
&lt;span style=&quot;font-family: &#39;Courier New&#39;, Courier, monospace;&quot;&gt;Writing objects: 100% (5/5), 514 bytes, done.&lt;/span&gt;&lt;br /&gt;
&lt;span style=&quot;font-family: &#39;Courier New&#39;, Courier, monospace;&quot;&gt;Total 5 (delta 3), reused 0 (delta 0)&lt;/span&gt;&lt;br /&gt;
&lt;span style=&quot;font-family: &#39;Courier New&#39;, Courier, monospace;&quot;&gt;&lt;br /&gt;
&lt;/span&gt;&lt;br /&gt;
&lt;span style=&quot;font-family: &#39;Courier New&#39;, Courier, monospace;&quot;&gt;-----&amp;gt; Heroku receiving push&lt;/span&gt;&lt;br /&gt;
&lt;span style=&quot;font-family: &#39;Courier New&#39;, Courier, monospace;&quot;&gt;-----&amp;gt; Fetching custom buildpack... done&lt;/span&gt;&lt;br /&gt;
&lt;span style=&quot;font-family: &#39;Courier New&#39;, Courier, monospace;&quot;&gt;-----&amp;gt; Mono app detected&lt;/span&gt;&lt;br /&gt;
&lt;span style=&quot;font-family: &#39;Courier New&#39;, Courier, monospace;&quot;&gt;-----&amp;gt; Fetching Mono binaries&lt;/span&gt;&lt;br /&gt;
&lt;span style=&quot;font-family: &#39;Courier New&#39;, Courier, monospace;&quot;&gt;tar: Ignoring unknown extended header keyword `SCHILY.dev&#39;&lt;/span&gt;&lt;br /&gt;
&lt;span style=&quot;font-family: &#39;Courier New&#39;, Courier, monospace;&quot;&gt;tar: Ignoring unknown extended header keyword `SCHILY.ino&#39;&lt;/span&gt;&lt;br /&gt;
&lt;span style=&quot;font-family: &#39;Courier New&#39;, Courier, monospace;&quot;&gt;tar: Ignoring unknown extended header keyword `SCHILY.nlink&#39;&lt;/span&gt;&lt;br /&gt;
&lt;span style=&quot;font-family: &#39;Courier New&#39;, Courier, monospace;&quot;&gt;tar: Ignoring unknown extended header keyword `SCHILY.dev&#39;&lt;/span&gt;&lt;br /&gt;
&lt;span style=&quot;font-family: &#39;Courier New&#39;, Courier, monospace;&quot;&gt;tar: Ignoring unknown extended header keyword `SCHILY.ino&#39;&lt;/span&gt;&lt;br /&gt;
&lt;span style=&quot;font-family: &#39;Courier New&#39;, Courier, monospace;&quot;&gt;tar: Ignoring unknown extended header keyword `SCHILY.nlink&#39;&lt;/span&gt;&lt;br /&gt;
&lt;span style=&quot;font-family: &#39;Courier New&#39;, Courier, monospace;&quot;&gt;tar: Ignoring unknown extended header keyword `SCHILY.dev&#39;&lt;/span&gt;&lt;br /&gt;
&lt;span style=&quot;font-family: &#39;Courier New&#39;, Courier, monospace;&quot;&gt;tar: Ignoring unknown extended header keyword `SCHILY.ino&#39;&lt;/span&gt;&lt;br /&gt;
&lt;span style=&quot;font-family: &#39;Courier New&#39;, Courier, monospace;&quot;&gt;tar: Ignoring unknown extended header keyword `SCHILY.nlink&#39;&lt;/span&gt;&lt;br /&gt;
&lt;span style=&quot;font-family: &#39;Courier New&#39;, Courier, monospace;&quot;&gt;tar: Ignoring unknown extended header keyword `SCHILY.dev&#39;&lt;/span&gt;&lt;br /&gt;
&lt;span style=&quot;font-family: &#39;Courier New&#39;, Courier, monospace;&quot;&gt;tar: Ignoring unknown extended header keyword `SCHILY.ino&#39;&lt;/span&gt;&lt;br /&gt;
&lt;span style=&quot;font-family: &#39;Courier New&#39;, Courier, monospace;&quot;&gt;tar: Ignoring unknown extended header keyword `SCHILY.nlink&#39;&lt;/span&gt;&lt;br /&gt;
&lt;span style=&quot;font-family: &#39;Courier New&#39;, Courier, monospace;&quot;&gt;tar: Ignoring unknown extended header keyword `SCHILY.dev&#39;&lt;/span&gt;&lt;br /&gt;
&lt;span style=&quot;font-family: &#39;Courier New&#39;, Courier, monospace;&quot;&gt;tar: Ignoring unknown extended header keyword `SCHILY.ino&#39;&lt;/span&gt;&lt;br /&gt;
&lt;span style=&quot;font-family: &#39;Courier New&#39;, Courier, monospace;&quot;&gt;tar: Ignoring unknown extended header keyword `SCHILY.nlink&#39;&lt;/span&gt;&lt;br /&gt;
&lt;span style=&quot;font-family: &#39;Courier New&#39;, Courier, monospace;&quot;&gt;tar: Ignoring unknown extended header keyword `SCHILY.dev&#39;&lt;/span&gt;&lt;br /&gt;
&lt;span style=&quot;font-family: &#39;Courier New&#39;, Courier, monospace;&quot;&gt;tar: Ignoring unknown extended header keyword `SCHILY.ino&#39;&lt;/span&gt;&lt;br /&gt;
&lt;span style=&quot;font-family: &#39;Courier New&#39;, Courier, monospace;&quot;&gt;tar: Ignoring unknown extended header keyword `SCHILY.nlink&#39;&lt;/span&gt;&lt;br /&gt;
&lt;span style=&quot;font-family: &#39;Courier New&#39;, Courier, monospace;&quot;&gt;tar: Ignoring unknown extended header keyword `SCHILY.dev&#39;&lt;/span&gt;&lt;br /&gt;
&lt;span style=&quot;font-family: &#39;Courier New&#39;, Courier, monospace;&quot;&gt;tar: Ignoring unknown extended header keyword `SCHILY.ino&#39;&lt;/span&gt;&lt;br /&gt;
&lt;span style=&quot;font-family: &#39;Courier New&#39;, Courier, monospace;&quot;&gt;tar: Ignoring unknown extended header keyword `SCHILY.nlink&#39;&lt;/span&gt;&lt;br /&gt;
&lt;span style=&quot;font-family: &#39;Courier New&#39;, Courier, monospace;&quot;&gt;tar: Ignoring unknown extended header keyword `SCHILY.dev&#39;&lt;/span&gt;&lt;br /&gt;
&lt;span style=&quot;font-family: &#39;Courier New&#39;, Courier, monospace;&quot;&gt;tar: Ignoring unknown extended header keyword `SCHILY.ino&#39;&lt;/span&gt;&lt;br /&gt;
&lt;span style=&quot;font-family: &#39;Courier New&#39;, Courier, monospace;&quot;&gt;tar: Ignoring unknown extended header keyword `SCHILY.nlink&#39;&lt;/span&gt;&lt;br /&gt;
&lt;span style=&quot;font-family: &#39;Courier New&#39;, Courier, monospace;&quot;&gt;tar: Ignoring unknown extended header keyword `SCHILY.dev&#39;&lt;/span&gt;&lt;br /&gt;
&lt;span style=&quot;font-family: &#39;Courier New&#39;, Courier, monospace;&quot;&gt;tar: Ignoring unknown extended header keyword `SCHILY.ino&#39;&lt;/span&gt;&lt;br /&gt;
&lt;span style=&quot;font-family: &#39;Courier New&#39;, Courier, monospace;&quot;&gt;tar: Ignoring unknown extended header keyword `SCHILY.nlink&#39;&lt;/span&gt;&lt;br /&gt;
&lt;span style=&quot;font-family: &#39;Courier New&#39;, Courier, monospace;&quot;&gt;-----&amp;gt; Vendoring mono 2.10.8&lt;/span&gt;&lt;br /&gt;
&lt;span style=&quot;font-family: &#39;Courier New&#39;, Courier, monospace;&quot;&gt;-----&amp;gt; building via /tmp/mono-GssQ/bin/mono /tmp/mono-GssQ/lib/mono/4.0/xbuild.exe /tmp/build_19y6xv4nr43ic/Nancy.Demo.Hosting.Self.sln&lt;/span&gt;&lt;br /&gt;
&lt;span style=&quot;font-family: &#39;Courier New&#39;, Courier, monospace;&quot;&gt;XBuild Engine Version 2.10.8.0&lt;/span&gt;&lt;br /&gt;
&lt;span style=&quot;font-family: &#39;Courier New&#39;, Courier, monospace;&quot;&gt;Mono, Version 2.10.8.0&lt;/span&gt;&lt;br /&gt;
&lt;span style=&quot;font-family: &#39;Courier New&#39;, Courier, monospace;&quot;&gt;Copyright (C) Marek Sieradzki 2005-2008, Novell 2008-2011.&lt;/span&gt;&lt;br /&gt;
&lt;span style=&quot;font-family: &#39;Courier New&#39;, Courier, monospace;&quot;&gt;&lt;br /&gt;
&lt;/span&gt;&lt;br /&gt;
&lt;span style=&quot;font-family: &#39;Courier New&#39;, Courier, monospace;&quot;&gt;Build started 01/03/2012 16:28:24.&lt;/span&gt;&lt;br /&gt;
&lt;span style=&quot;font-family: &#39;Courier New&#39;, Courier, monospace;&quot;&gt;__________________________________________________&lt;/span&gt;&lt;br /&gt;
&lt;span style=&quot;font-family: &#39;Courier New&#39;, Courier, monospace;&quot;&gt;Project &quot;/tmp/build_19y6xv4nr43ic/Nancy.Demo.Hosting.Self.sln&quot; (default target(s)):&lt;/span&gt;&lt;br /&gt;
&lt;span style=&quot;font-family: &#39;Courier New&#39;, Courier, monospace;&quot;&gt;Target ValidateSolutionConfiguration:&lt;/span&gt;&lt;br /&gt;
&lt;span style=&quot;font-family: &#39;Courier New&#39;, Courier, monospace;&quot;&gt;Building solution configuration &quot;Debug|Mixed Platforms&quot;.&lt;/span&gt;&lt;br /&gt;
&lt;span style=&quot;font-family: &#39;Courier New&#39;, Courier, monospace;&quot;&gt;Target Build:&lt;/span&gt;&lt;br /&gt;
&lt;span style=&quot;font-family: &#39;Courier New&#39;, Courier, monospace;&quot;&gt;Project &quot;/tmp/build_19y6xv4nr43ic/src/Nancy.Demo.Hosting.Self.csproj&quot; (default target(s)):&lt;/span&gt;&lt;br /&gt;
&lt;span style=&quot;font-family: &#39;Courier New&#39;, Courier, monospace;&quot;&gt;Target PrepareForBuild:&lt;/span&gt;&lt;br /&gt;
&lt;span style=&quot;font-family: &#39;Courier New&#39;, Courier, monospace;&quot;&gt;Configuration: Debug Platform: x86&lt;/span&gt;&lt;br /&gt;
&lt;span style=&quot;font-family: &#39;Courier New&#39;, Courier, monospace;&quot;&gt;Created directory &quot;bin/&quot;&lt;/span&gt;&lt;br /&gt;
&lt;span style=&quot;font-family: &#39;Courier New&#39;, Courier, monospace;&quot;&gt;Created directory &quot;obj/x86/Debug/&quot;&lt;/span&gt;&lt;br /&gt;
&lt;span style=&quot;font-family: &#39;Courier New&#39;, Courier, monospace;&quot;&gt;Target CopyFilesMarkedCopyLocal:&lt;/span&gt;&lt;br /&gt;
&lt;span style=&quot;font-family: &#39;Courier New&#39;, Courier, monospace;&quot;&gt;Copying file from &#39;/tmp/build_19y6xv4nr43ic/lib/Nancy.dll&#39; to &#39;/tmp/build_19y6xv4nr43ic/src/bin/Nancy.dll&#39;&lt;/span&gt;&lt;br /&gt;
&lt;span style=&quot;font-family: &#39;Courier New&#39;, Courier, monospace;&quot;&gt;Copying file from &#39;/tmp/build_19y6xv4nr43ic/lib/Nancy.Hosting.Self.dll&#39; to &#39;/tmp/build_19y6xv4nr43ic/src/bin/Nancy.Hosting.Self.dll&#39;&lt;/span&gt;&lt;br /&gt;
&lt;span style=&quot;font-family: &#39;Courier New&#39;, Courier, monospace;&quot;&gt;Target GenerateSatelliteAssemblies:&lt;/span&gt;&lt;br /&gt;
&lt;span style=&quot;font-family: &#39;Courier New&#39;, Courier, monospace;&quot;&gt;No input files were specified for target GenerateSatelliteAssemblies, skipping.&lt;/span&gt;&lt;br /&gt;
&lt;span style=&quot;font-family: &#39;Courier New&#39;, Courier, monospace;&quot;&gt;Target CoreCompile:&lt;/span&gt;&lt;br /&gt;
&lt;span style=&quot;font-family: &#39;Courier New&#39;, Courier, monospace;&quot;&gt;Tool /tmp/mono-GssQ/bin/dmcs execution started with arguments: /noconfig /debug:full /debug+ /optimize- /out:obj/x86/Debug/Nancy.Demo.Hosting.Self.exe Program.cs TestModule.cs /target:exe /define:&quot;DEBUG;TRACE&quot; /main:Nancy.Demo.Hosting.Self.Program /platform:x86 /reference:/tmp/mono-GssQ/lib/mono/4.0/System.dll /reference:../lib/Nancy.dll /reference:../lib/Nancy.Hosting.Self.dll /reference:/tmp/mono-GssQ/lib/mono/4.0/System.Xml.Linq.dll /reference:/tmp/mono-GssQ/lib/mono/4.0/System.Data.DataSetExtensions.dll /reference:/tmp/mono-GssQ/lib/mono/4.0/Microsoft.CSharp.dll /reference:/tmp/mono-GssQ/lib/mono/4.0/System.Data.dll /reference:/tmp/mono-GssQ/lib/mono/4.0/System.Xml.dll /reference:/tmp/mono-GssQ/lib/mono/4.0/System.Core.dll /reference:/tmp/mono-GssQ/lib/mono/4.0/mscorlib.dll /warn:4&lt;/span&gt;&lt;br /&gt;
&lt;span style=&quot;font-family: &#39;Courier New&#39;, Courier, monospace;&quot;&gt;Target _CopyDeployFilesToOutputDirectoryAlways:&lt;/span&gt;&lt;br /&gt;
&lt;span style=&quot;font-family: &#39;Courier New&#39;, Courier, monospace;&quot;&gt;Creating directory &#39;/tmp/build_19y6xv4nr43ic/src/bin/Views&#39;&lt;/span&gt;&lt;br /&gt;
&lt;span style=&quot;font-family: &#39;Courier New&#39;, Courier, monospace;&quot;&gt;Copying file from &#39;/tmp/build_19y6xv4nr43ic/src/Views/staticview.html&#39; to &#39;/tmp/build_19y6xv4nr43ic/src/bin/Views/staticview.html&#39;&lt;/span&gt;&lt;br /&gt;
&lt;span style=&quot;font-family: &#39;Courier New&#39;, Courier, monospace;&quot;&gt;Target _CopyAppConfigFile:&lt;/span&gt;&lt;br /&gt;
&lt;span style=&quot;font-family: &#39;Courier New&#39;, Courier, monospace;&quot;&gt;Copying file from &#39;/tmp/build_19y6xv4nr43ic/src/app.config&#39; to &#39;/tmp/build_19y6xv4nr43ic/src/bin/Nancy.Demo.Hosting.Self.exe.config&#39;&lt;/span&gt;&lt;br /&gt;
&lt;span style=&quot;font-family: &#39;Courier New&#39;, Courier, monospace;&quot;&gt;Target DeployOutputFiles:&lt;/span&gt;&lt;br /&gt;
&lt;span style=&quot;font-family: &#39;Courier New&#39;, Courier, monospace;&quot;&gt;Copying file from &#39;/tmp/build_19y6xv4nr43ic/src/obj/x86/Debug/Nancy.Demo.Hosting.Self.exe.mdb&#39; to &#39;/tmp/build_19y6xv4nr43ic/src/bin/Nancy.Demo.Hosting.Self.exe.mdb&#39;&lt;/span&gt;&lt;br /&gt;
&lt;span style=&quot;font-family: &#39;Courier New&#39;, Courier, monospace;&quot;&gt;Copying file from &#39;/tmp/build_19y6xv4nr43ic/src/obj/x86/Debug/Nancy.Demo.Hosting.Self.exe&#39; to &#39;/tmp/build_19y6xv4nr43ic/src/bin/Nancy.Demo.Hosting.Self.exe&#39;&lt;/span&gt;&lt;br /&gt;
&lt;span style=&quot;font-family: &#39;Courier New&#39;, Courier, monospace;&quot;&gt;Done building project &quot;/tmp/build_19y6xv4nr43ic/src/Nancy.Demo.Hosting.Self.csproj&quot;.&lt;/span&gt;&lt;br /&gt;
&lt;span style=&quot;font-family: &#39;Courier New&#39;, Courier, monospace;&quot;&gt;Done building project &quot;/tmp/build_19y6xv4nr43ic/Nancy.Demo.Hosting.Self.sln&quot;.&lt;/span&gt;&lt;br /&gt;
&lt;span style=&quot;font-family: &#39;Courier New&#39;, Courier, monospace;&quot;&gt;&lt;br /&gt;
&lt;/span&gt;&lt;br /&gt;
&lt;span style=&quot;font-family: &#39;Courier New&#39;, Courier, monospace;&quot;&gt;Build succeeded.&lt;/span&gt;&lt;br /&gt;
&lt;span style=&quot;font-family: &#39;Courier New&#39;, Courier, monospace;&quot;&gt;0 Warning(s)&lt;/span&gt;&lt;br /&gt;
&lt;span style=&quot;font-family: &#39;Courier New&#39;, Courier, monospace;&quot;&gt;0 Error(s)&lt;/span&gt;&lt;br /&gt;
&lt;span style=&quot;font-family: &#39;Courier New&#39;, Courier, monospace;&quot;&gt;&lt;br /&gt;
&lt;/span&gt;&lt;br /&gt;
&lt;span style=&quot;font-family: &#39;Courier New&#39;, Courier, monospace;&quot;&gt;Time Elapsed 00:00:01.0730530&lt;/span&gt;&lt;br /&gt;
&lt;span style=&quot;font-family: &#39;Courier New&#39;, Courier, monospace;&quot;&gt;-----&amp;gt; Discovering process types&lt;/span&gt;&lt;br /&gt;
&lt;span style=&quot;font-family: &#39;Courier New&#39;, Courier, monospace;&quot;&gt;Procfile declares types -&amp;gt; local, web&lt;/span&gt;&lt;br /&gt;
&lt;span style=&quot;font-family: &#39;Courier New&#39;, Courier, monospace;&quot;&gt;-----&amp;gt; Compiled slug size is 78.3MB&lt;/span&gt;&lt;br /&gt;
&lt;span style=&quot;font-family: &#39;Courier New&#39;, Courier, monospace;&quot;&gt;-----&amp;gt; Launching... done, v18&lt;/span&gt;&lt;br /&gt;
&lt;span style=&quot;font-family: &#39;Courier New&#39;, Courier, monospace;&quot;&gt;http://deep-moon-1452.herokuapp.com deployed to Heroku&lt;/span&gt;&lt;br /&gt;
&lt;span style=&quot;font-family: &#39;Courier New&#39;, Courier, monospace;&quot;&gt;&lt;br /&gt;
&lt;/span&gt;&lt;br /&gt;
&lt;span style=&quot;font-family: &#39;Courier New&#39;, Courier, monospace;&quot;&gt;To git@heroku.com:deep-moon-1452.git&lt;/span&gt;&lt;br /&gt;
&lt;span style=&quot;font-family: &#39;Courier New&#39;, Courier, monospace;&quot;&gt;4d9e07b..6ce44e4  master -&amp;gt; master&lt;/span&gt;&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;</content><link rel='replies' type='application/atom+xml' href='http://blog.benhall.me.uk/feeds/1852698578104564876/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment/fullpage/post/21967381/1852698578104564876' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/21967381/posts/default/1852698578104564876'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/21967381/posts/default/1852698578104564876'/><link rel='alternate' type='text/html' href='http://blog.benhall.me.uk/2012/01/experiment-deploying-c-mono-on-heroku.html' title='Experiment: Deploying C# / Mono on Heroku'/><author><name>Ben Hall</name><uri>http://www.blogger.com/profile/17734933641904484310</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='23' height='32' src='//blogger.googleusercontent.com/img/b/R29vZ2xl/AVvXsEiAHZKs2vYlTA1W58oZ3_laZ-JNsUCxXJj__UyIx7TgHEw6DD9nNDr5ML4vvTpu7HbXx0Q5FIWAXyJ2xRsiX97Iu12TNYdSZuMywoqD7Khsbz936TzlIJOBTkDINgB1iYc/s220/n792665715_5219640_7493.jpg'/></author><media:thumbnail xmlns:media="http://search.yahoo.com/mrss/" url="https://blogger.googleusercontent.com/img/b/R29vZ2xl/AVvXsEhipxK-uHdH6QAUy_nAtMr3TzU7alDv7L8D7SDYiH5-CUSnWBswlOf8LWHZagAVh5Nsrz7Ucobh-fPY5m3k_u4cLM0DdMhyM-seMEQGjYaOq0EzL614xkusDaSkfWAHRRNOpM4l/s72-c/nancy_heroku_v1.png" height="72" width="72"/><thr:total>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-21967381.post-2875174802475643017</id><published>2012-01-01T15:31:00.003+00:00</published><updated>2012-01-01T15:31:43.204+00:00</updated><title type='text'>2011 - An Unexpected Journey</title><content type='html'>When I started this post I wanted to reflect on the interesting year I&#39;ve had. I wanted to talk about how launching a start-up had taught me so much about business, technology and myself. I wanted to go on and cover how it has also meant making sacrifices, such as missing Glastonbury even when I had a ticket and cutting back on spending, blogging, open source and conference speaking - the things I really enjoy. Finally, I wanted to end with how start-up life has sometimes meant working in isolation and at times being demotivated and stressed with how everything was going.&lt;br /&gt;
&lt;br /&gt;
However, while it&#39;s important for me to look back I also want to focus on looking forward which can be summed up by this tweet: &lt;br /&gt;
&lt;br /&gt;
&lt;blockquote class=&quot;twitter-tweet tw-align-center&quot;&gt;
#2012 Release more. Blog more. Drink more. Earn more.&lt;br /&gt;
— Ben Hall (@Ben_Hall) &lt;a data-datetime=&quot;2012-01-01T00:42:51+00:00&quot; href=&quot;https://twitter.com/Ben_Hall/status/153274953997877249&quot;&gt;January 1, 2012&lt;/a&gt;&lt;/blockquote&gt;
&lt;script charset=&quot;utf-8&quot; src=&quot;//platform.twitter.com/widgets.js&quot;&gt;
&lt;/script&gt;&lt;br /&gt;
&lt;br /&gt;
To get the ball rolling, interested in hiring me? Send me an email at blog@benhall.me.uk&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;</content><link rel='replies' type='application/atom+xml' href='http://blog.benhall.me.uk/feeds/2875174802475643017/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment/fullpage/post/21967381/2875174802475643017' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/21967381/posts/default/2875174802475643017'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/21967381/posts/default/2875174802475643017'/><link rel='alternate' type='text/html' href='http://blog.benhall.me.uk/2012/01/2011-unexpected-journey.html' title='2011 - An Unexpected Journey'/><author><name>Ben Hall</name><uri>http://www.blogger.com/profile/17734933641904484310</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='23' height='32' src='//blogger.googleusercontent.com/img/b/R29vZ2xl/AVvXsEiAHZKs2vYlTA1W58oZ3_laZ-JNsUCxXJj__UyIx7TgHEw6DD9nNDr5ML4vvTpu7HbXx0Q5FIWAXyJ2xRsiX97Iu12TNYdSZuMywoqD7Khsbz936TzlIJOBTkDINgB1iYc/s220/n792665715_5219640_7493.jpg'/></author><thr:total>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-21967381.post-6213541409792286733</id><published>2011-10-10T12:11:00.000+00:00</published><updated>2011-10-10T12:11:32.751+00:00</updated><category scheme="http://www.blogger.com/atom/ns#" term="AWS"/><category scheme="http://www.blogger.com/atom/ns#" term="DDDNorth"/><title type='text'>Slides on Amazon Web Services (AWS) from DDD North</title><content type='html'>This weekend I had the pleasure of presenting on Amazon Web Services at DDD North. Please find my slides below which discusses S3, EC2, some architecture and other services provided by AWS.&lt;br /&gt;
&lt;br /&gt;
If you have any questions, please ping me an email or tweet.&lt;br /&gt;
&lt;br /&gt;
&lt;div id=&quot;__ss_9620802&quot; style=&quot;width: 425px;&quot;&gt;
&lt;strong style=&quot;display: block; margin: 12px 0 4px;&quot;&gt;&lt;a href=&quot;http://www.slideshare.net/BenHalluk/taking-advantage-of-the-amazon-web-services-aws-family&quot; target=&quot;_blank&quot; title=&quot;Taking advantage of the Amazon Web Services (AWS) Family&quot;&gt;Taking advantage of the Amazon Web Services (AWS) Family&lt;/a&gt;&lt;/strong&gt; &lt;iframe frameborder=&quot;0&quot; height=&quot;355&quot; marginheight=&quot;0&quot; marginwidth=&quot;0&quot; scrolling=&quot;no&quot; src=&quot;http://www.slideshare.net/slideshow/embed_code/9620802&quot; width=&quot;425&quot;&gt;&lt;/iframe&gt; &lt;br /&gt;
&lt;div style=&quot;padding: 5px 0 12px;&quot;&gt;
View more &lt;a href=&quot;http://www.slideshare.net/&quot; target=&quot;_blank&quot;&gt;presentations&lt;/a&gt; from &lt;a href=&quot;http://www.slideshare.net/BenHalluk&quot; target=&quot;_blank&quot;&gt;BenHalluk&lt;/a&gt; &lt;/div&gt;
&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://blog.benhall.me.uk/feeds/6213541409792286733/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment/fullpage/post/21967381/6213541409792286733' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/21967381/posts/default/6213541409792286733'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/21967381/posts/default/6213541409792286733'/><link rel='alternate' type='text/html' href='http://blog.benhall.me.uk/2011/10/slides-on-amazon-web-services-aws-from.html' title='Slides on Amazon Web Services (AWS) from DDD North'/><author><name>Ben Hall</name><uri>http://www.blogger.com/profile/17734933641904484310</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='23' height='32' src='//blogger.googleusercontent.com/img/b/R29vZ2xl/AVvXsEiAHZKs2vYlTA1W58oZ3_laZ-JNsUCxXJj__UyIx7TgHEw6DD9nNDr5ML4vvTpu7HbXx0Q5FIWAXyJ2xRsiX97Iu12TNYdSZuMywoqD7Khsbz936TzlIJOBTkDINgB1iYc/s220/n792665715_5219640_7493.jpg'/></author><thr:total>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-21967381.post-7802741441358791418</id><published>2011-08-31T11:14:00.001+00:00</published><updated>2011-08-31T11:15:30.300+00:00</updated><category scheme="http://www.blogger.com/atom/ns#" term="maydayhq"/><title type='text'>Join @maydayhq as a start-up co-founder</title><content type='html'>&lt;b&gt;&lt;i&gt;Cross-posted with&amp;nbsp;&lt;a href=&quot;http://blog.maydayhq.com/2011/08/31/join-mayday-as-a-start-up-co-founder/&quot;&gt;http://blog.maydayhq.com/2011/08/31/join-mayday-as-a-start-up-co-founder/&lt;/a&gt;&lt;/i&gt;&lt;/b&gt;&lt;br /&gt;
&lt;br /&gt;
We currently have an exciting opportunity to join the founding team of Mayday. Ideally, the person would bring a level of visual design / UI / UX expertise in the role of a front-end developer and help us build an amazing product. As a co-founder, you’ll be a key member of the company at an early stage, involved in building the vision, product and the company.&lt;br /&gt;
&lt;br /&gt;
The product is SaaS-based, enabling clients to improve their website by alerting them when and where users experience problems. Combining lightweight integration with ‘Big Data’ technologies, we monitor users engagement, interaction and client details allowing us to identity why they’re having problems.&lt;br /&gt;
Our concept is still evolving, and you’ll be in a position to make your mark. Mayday has the potential to have a huge impact on development, testing and production systems and impact how we handle modern software issues and their related testing concerns.&lt;br /&gt;
&lt;br /&gt;
Mayday recently graduated from the Springboard Accelerator Programme in Cambridge and has been covered by sites including TechCrunch and TheNextWeb. The next stages for the company involve a funding round, building an amazing team to allow us to change the world and then achieving profit. The product is currently an early alpha, with a small number of users providing valuable feedback before opening it up to the private invite list. A demo is available at &lt;a href=&quot;http://app.maydayhq.com/demo&quot;&gt;http://app.maydayhq.com/demo&lt;/a&gt;&lt;br /&gt;
&lt;br /&gt;
Key characteristics for the role include:&lt;br /&gt;
- Passionate about startups. Building a company is amazing and extremely rewarding, but it takes a certain type of person.&lt;br /&gt;
- Passionate about building amazing products and changing the world.&lt;br /&gt;
- Capable of producing amazing visual design.&lt;br /&gt;
- Capable of turning an amazing visual design into reality via HTML, CSS, Javascript and any other cool tools you fancy.&lt;br /&gt;
- Understands the importance of UX, workflows and the key metrics required to monitor and improve.&lt;br /&gt;
- Self motivated, proactive while taking pride in their work and looking for ways to learn / improve.&lt;br /&gt;
&lt;br /&gt;
Remuneration: Variable; let’s discuss. As a co-founder you’ll be a key part of the business with significant founder share options available.&lt;br /&gt;
&lt;br /&gt;
Location: Old Street, London (open minded to other locations.)&lt;br /&gt;
&lt;strong&gt;&lt;br /&gt;&lt;/strong&gt;&lt;br /&gt;
&lt;strong&gt;Interested?&lt;/strong&gt;&lt;br /&gt;
Email &lt;strong&gt;workwithus {at} Maydayhq.com&lt;/strong&gt; and tell us about yourself. It would be great to hear about recent projects you’ve been excited about, examples of your work and links to github, Twitter, LinkedIn, blog etc.&lt;br /&gt;
&lt;br /&gt;
Why not add something different to the mix by telling us what features you would love to see in Mayday and how you see it growing over the next few years? What other startups currently excite you and why?&lt;br /&gt;
&lt;br /&gt;
If you don’t fit the role of front-end developer, but feel you could make a difference to the company and add value in a different role, please email and tell us – we’d love to hear from you!</content><link rel='replies' type='application/atom+xml' href='http://blog.benhall.me.uk/feeds/7802741441358791418/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment/fullpage/post/21967381/7802741441358791418' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/21967381/posts/default/7802741441358791418'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/21967381/posts/default/7802741441358791418'/><link rel='alternate' type='text/html' href='http://blog.benhall.me.uk/2011/08/join-maydayhq-as-start-up-co-founder.html' title='Join @maydayhq as a start-up co-founder'/><author><name>Ben Hall</name><uri>http://www.blogger.com/profile/17734933641904484310</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='23' height='32' src='//blogger.googleusercontent.com/img/b/R29vZ2xl/AVvXsEiAHZKs2vYlTA1W58oZ3_laZ-JNsUCxXJj__UyIx7TgHEw6DD9nNDr5ML4vvTpu7HbXx0Q5FIWAXyJ2xRsiX97Iu12TNYdSZuMywoqD7Khsbz936TzlIJOBTkDINgB1iYc/s220/n792665715_5219640_7493.jpg'/></author><thr:total>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-21967381.post-5260025540668607848</id><published>2011-08-17T15:03:00.000+00:00</published><updated>2011-08-17T15:03:48.024+00:00</updated><category scheme="http://www.blogger.com/atom/ns#" term="unix"/><title type='text'>Count number of times a file has been download via HTTP logs</title><content type='html'>Today, I wanted to find out how many times a file had been downloaded from a web server. &amp;nbsp;Without Google Analytics, it was time to pull out the big guns - grep.&lt;br /&gt;
&lt;br /&gt;
The command I used was:&lt;br /&gt;
&lt;br /&gt;
grep -o /e.js /var/log/lighttpd/access.log | wc -w&lt;br /&gt;
&lt;br /&gt;
/e.js is the file I&#39;m interested in, while&amp;nbsp;access.log is the file.&lt;br /&gt;
&lt;br /&gt;
The output of grep will be a long list of the string /e.js to indicate the matches. &amp;nbsp;wc counts number of words. With the use of the pipe, you have a lovely quick command to find out how many times a file has been downloaded via your logs.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;</content><link rel='replies' type='application/atom+xml' href='http://blog.benhall.me.uk/feeds/5260025540668607848/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment/fullpage/post/21967381/5260025540668607848' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/21967381/posts/default/5260025540668607848'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/21967381/posts/default/5260025540668607848'/><link rel='alternate' type='text/html' href='http://blog.benhall.me.uk/2011/08/count-number-of-times-file-has-been.html' title='Count number of times a file has been download via HTTP logs'/><author><name>Ben Hall</name><uri>http://www.blogger.com/profile/17734933641904484310</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='23' height='32' src='//blogger.googleusercontent.com/img/b/R29vZ2xl/AVvXsEiAHZKs2vYlTA1W58oZ3_laZ-JNsUCxXJj__UyIx7TgHEw6DD9nNDr5ML4vvTpu7HbXx0Q5FIWAXyJ2xRsiX97Iu12TNYdSZuMywoqD7Khsbz936TzlIJOBTkDINgB1iYc/s220/n792665715_5219640_7493.jpg'/></author><thr:total>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-21967381.post-265944688278319539</id><published>2011-08-15T19:31:00.001+00:00</published><updated>2011-08-15T19:32:02.978+00:00</updated><category scheme="http://www.blogger.com/atom/ns#" term="sxsw"/><category scheme="http://www.blogger.com/atom/ns#" term="sxsw2012"/><title type='text'>SXSW 2012 Proposal: Lean Testing</title><content type='html'>For the past few years I&#39;ve been kicking myself for not attending South-by-Southwest (SXSW). Every year it sounds like an amazing conference, so this year I decided to submit a talk - what&#39;s the worse that could happen?&lt;br /&gt;
&lt;br /&gt;
The session is titled &quot;&lt;span style=&quot;background-color: white; color: #ff6600; font-family: &#39;Lucida Grande&#39;, &#39;Lucida Sans Unicode&#39;, Arial, Verdana, sans-serif; font-size: 16px; font-weight: bold;&quot;&gt;How Lean Testing removes waste and software bugs&lt;/span&gt;&quot; where I&#39;ll discuss how to take a lean approach to testing and how it can enable you to remove the waste causing delays to releasing and delays to customer feedback among other things. Over the next few months I&#39;ll be blogging related items here and on the &lt;a href=&quot;http://blog.maydayhq.com/&quot;&gt;Mayday&lt;/a&gt; blog.&lt;br /&gt;
&lt;br /&gt;
As such, I have a request. SXSW receive a huge amount of sessions every year. To help, they ask for the community to vote. If you could take a moment to vote for my session proposal then I would be most grateful!! &lt;a href=&quot;http://bit.ly/leantestingsxsw2012&quot;&gt;http://bit.ly/leantestingsxsw2012&lt;/a&gt;&lt;br /&gt;
&lt;br /&gt;
Every vote helps! Thank you!&lt;br /&gt;
&lt;br /&gt;</content><link rel='replies' type='application/atom+xml' href='http://blog.benhall.me.uk/feeds/265944688278319539/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment/fullpage/post/21967381/265944688278319539' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/21967381/posts/default/265944688278319539'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/21967381/posts/default/265944688278319539'/><link rel='alternate' type='text/html' href='http://blog.benhall.me.uk/2011/08/sxsw-2012-proposal-lean-testing.html' title='SXSW 2012 Proposal: Lean Testing'/><author><name>Ben Hall</name><uri>http://www.blogger.com/profile/17734933641904484310</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='23' height='32' src='//blogger.googleusercontent.com/img/b/R29vZ2xl/AVvXsEiAHZKs2vYlTA1W58oZ3_laZ-JNsUCxXJj__UyIx7TgHEw6DD9nNDr5ML4vvTpu7HbXx0Q5FIWAXyJ2xRsiX97Iu12TNYdSZuMywoqD7Khsbz936TzlIJOBTkDINgB1iYc/s220/n792665715_5219640_7493.jpg'/></author><thr:total>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-21967381.post-6571059941289371288</id><published>2011-08-10T12:57:00.003+00:00</published><updated>2011-08-10T13:12:22.240+00:00</updated><title type='text'>First play with the Cloud-Based Amazon Reader</title><content type='html'>In the last few hours Amazon&amp;nbsp;&lt;a href=&quot;http://techcrunch.com/2011/08/09/kindle-cloud-reader/&quot;&gt;announced&lt;/a&gt;&amp;nbsp;their &quot;Cloud Reader&quot;, enabling you to read your Kindle collection from a browser. Sounds great, but what&#39;s the implementation like?&lt;br /&gt;
&lt;span class=&quot;Apple-style-span&quot; style=&quot;font-size: large;&quot;&gt;&lt;b&gt;Webkit based means no Firefox&lt;/b&gt;&lt;/span&gt;&lt;br /&gt;
Firstly they&#39;re promoting it as a web-based reader, however with their use of WebSQL database they only support Chrome and Safari. Attempting to use the service using the FireFox 8 Nightly builds results in the message &quot;&lt;strong&gt;Your web browser isn&#39;t supported yet.&lt;/strong&gt; Download Chrome or Safari below.&quot;. &lt;br /&gt;
Initially I was surprised they didn&#39;t use an abstraction layer allowing them to support IndexDB (Firefox \ IE) and WebSQL (Webkit). From reading articles, it looks like their target market is tablet devices meaning Webkit based browsers, making supporting only WebSQL an obvious choice. This is an important point for developers -&amp;nbsp;&lt;a href=&quot;http://twitter.com/intent/tweet?text=&#39;Understand%20your%20user-base%20when%20developing%20products&#39;%20via%20http://blog.benhall.me.uk/%20and%20@Ben_Hall&quot;&gt;understand your user-base when developing products&lt;/a&gt;. Release a product that works for your target audience, only add additional time and complexity if there is demand.&lt;br /&gt;
When I jumped into the product, there were a few more interesting surprises. I was shown was an option to setup Offline Reading. From a users point of view this was very surprising - most people would assume offline reading would be enabled by default.&lt;br /&gt;
Instead, it expects me to install a Chrome Extension. Amazon knows they will always have HTML5 and WebSQL available so I&#39;m guessing this allows them to get around DNS lookups when no wi-fi is found.&lt;br /&gt;
&lt;a href=&quot;https://blogger.googleusercontent.com/img/b/R29vZ2xl/AVvXsEgZ3_T3Ih957w3_rtcVpSk6uZMI6LOigMklaMgiPMgW0pLu2laC7Ou8K1scBEi4EbnQ2T71qvtc-W-hDl0E-xC2up57Xi94SVQdUUenV4itfpbGRX__jidalOm-Pe8cbkgTvngl/s1600/Offline_Reading.png&quot; imageanchor=&quot;1&quot; style=&quot;margin-bottom: 1em; margin-right: 1em;&quot;&gt;&lt;img border=&quot;0&quot; height=&quot;192&quot; src=&quot;https://blogger.googleusercontent.com/img/b/R29vZ2xl/AVvXsEgZ3_T3Ih957w3_rtcVpSk6uZMI6LOigMklaMgiPMgW0pLu2laC7Ou8K1scBEi4EbnQ2T71qvtc-W-hDl0E-xC2up57Xi94SVQdUUenV4itfpbGRX__jidalOm-Pe8cbkgTvngl/s320/Offline_Reading.png&quot; width=&quot;320&quot; /&gt;&lt;/a&gt;&lt;br /&gt;
&lt;a href=&quot;https://blogger.googleusercontent.com/img/b/R29vZ2xl/AVvXsEjsdKjL60rTuyD2wKMRZYzb7Gv_EGx3j-2WobYbtN9Zg2uYKDTK4f5vNJbosVCSsac0XHWSNP24swGMFl9EtJCSuCGJgbD4dfedR-Ia8Timice1UphylMsZljTd2Ze6_YCORoEG/s1600/cloud_reader.png&quot; imageanchor=&quot;1&quot; style=&quot;margin-bottom: 1em; margin-right: 1em;&quot;&gt;&lt;img border=&quot;0&quot; height=&quot;156&quot; src=&quot;https://blogger.googleusercontent.com/img/b/R29vZ2xl/AVvXsEjsdKjL60rTuyD2wKMRZYzb7Gv_EGx3j-2WobYbtN9Zg2uYKDTK4f5vNJbosVCSsac0XHWSNP24swGMFl9EtJCSuCGJgbD4dfedR-Ia8Timice1UphylMsZljTd2Ze6_YCORoEG/s320/cloud_reader.png&quot; width=&quot;320&quot; /&gt;&lt;/a&gt;&lt;br /&gt;
Sadly, after clicking Install I was shown a blank tab with no explanations and nothing listed under my browser extensions. Not a great experience. I do have an Amazon Reader WebApp icon, however this process feels &lt;b&gt;confusing and unnecessary&lt;/b&gt;&amp;nbsp;mainly because of the time within the journey they asked me but also the lack of indication from Chrome about if it&#39;s an App or Extension.&lt;br /&gt;
&lt;span class=&quot;Apple-style-span&quot; style=&quot;font-size: large;&quot;&gt;&lt;b&gt;Explicit Offline Mode&lt;/b&gt;&lt;/span&gt;&lt;br /&gt;
Within the reader the offline mode becomes even more confusing. They have made a separation between Cloud and Downloaded which makes sense with a large library but if your currently reading a book is that classed as cloud based or downloaded? From what I could tell it was cloud based which could become annoying. Having the separation of Cloud vs Available Offline would have made more sense based on other terms and phasing used in the application.&lt;br /&gt;
&lt;a href=&quot;https://blogger.googleusercontent.com/img/b/R29vZ2xl/AVvXsEioUprh2_Gqqc4eG6k9KvZlqRTpA_ssxQXbq7NApAqe2YcYBpowZO2roTa0QVmM_kJuXGKueHaOKDvpQ1w4viHbrEHHF1GNiFu2d2EycNe-E4GqzQ2pnO0F0LY_t6zvMAxpDrMe/s1600/Landing_page.png&quot; imageanchor=&quot;1&quot; style=&quot;margin-bottom: 1em; margin-right: 1em;&quot;&gt;&lt;img border=&quot;0&quot; height=&quot;199&quot; src=&quot;https://blogger.googleusercontent.com/img/b/R29vZ2xl/AVvXsEioUprh2_Gqqc4eG6k9KvZlqRTpA_ssxQXbq7NApAqe2YcYBpowZO2roTa0QVmM_kJuXGKueHaOKDvpQ1w4viHbrEHHF1GNiFu2d2EycNe-E4GqzQ2pnO0F0LY_t6zvMAxpDrMe/s320/Landing_page.png&quot; width=&quot;320&quot; /&gt;&lt;/a&gt;&lt;br /&gt;
&lt;br /&gt;
However, the reader is impressive. It shows how HTML5 and Javascript based applications can create compelling experiences, reaching beyond the web browser.&lt;br /&gt;
&lt;a href=&quot;https://blogger.googleusercontent.com/img/b/R29vZ2xl/AVvXsEhqNBB0xGE4Aew9wyYLotMuqbCaga2pmWqZTNeLZootP9WIxF7MADBiL_CrkG5BLooObonNc6bfEKgw64t-hCXbO0s_R-z7D7kGuNNpjKWGnFH5c-u1pSTV6_yDjZphRHn_mqDG/s1600/Highlighting.png&quot; imageanchor=&quot;1&quot; style=&quot;margin-bottom: 1em; margin-right: 1em;&quot;&gt;&lt;br /&gt;&lt;/a&gt;&lt;a href=&quot;https://blogger.googleusercontent.com/img/b/R29vZ2xl/AVvXsEhqNBB0xGE4Aew9wyYLotMuqbCaga2pmWqZTNeLZootP9WIxF7MADBiL_CrkG5BLooObonNc6bfEKgw64t-hCXbO0s_R-z7D7kGuNNpjKWGnFH5c-u1pSTV6_yDjZphRHn_mqDG/s1600/Highlighting.png&quot; imageanchor=&quot;1&quot; style=&quot;margin-bottom: 1em; margin-right: 1em;&quot;&gt;&lt;img border=&quot;0&quot; height=&quot;245&quot; src=&quot;https://blogger.googleusercontent.com/img/b/R29vZ2xl/AVvXsEhqNBB0xGE4Aew9wyYLotMuqbCaga2pmWqZTNeLZootP9WIxF7MADBiL_CrkG5BLooObonNc6bfEKgw64t-hCXbO0s_R-z7D7kGuNNpjKWGnFH5c-u1pSTV6_yDjZphRHn_mqDG/s320/Highlighting.png&quot; width=&quot;320&quot; /&gt;&lt;/a&gt;&lt;br /&gt;
Yet, with functionality such as reading&amp;nbsp;preferences&amp;nbsp;not being used across different browsers\devices the reader still has a long way to go.&lt;br /&gt;
&lt;span class=&quot;Apple-style-span&quot; style=&quot;font-size: large;&quot;&gt;&lt;b&gt;No wifi but still works&lt;/b&gt;&lt;/span&gt;&lt;br /&gt;
As proof of the potential, what actually happens when you don&#39;t have wifi? The first attempt was a complete failure.&lt;br /&gt;
&lt;a href=&quot;https://blogger.googleusercontent.com/img/b/R29vZ2xl/AVvXsEge8iyEEpo3dQ9siLEYTqlJtHV_4qNbfxVdsk1ltydQSouwdnxjAM2dpEEyZtBKtdK7G177Rs_-TKCzINwuIpqnzKVcgvPyDXfI0Zs53OiovDm-oFFNlMfpmlTXLg_wnAszycXP/s1600/No_wifi_no_app.png&quot; imageanchor=&quot;1&quot; style=&quot;margin-bottom: 1em; margin-right: 1em;&quot;&gt;&lt;img border=&quot;0&quot; height=&quot;166&quot; src=&quot;https://blogger.googleusercontent.com/img/b/R29vZ2xl/AVvXsEge8iyEEpo3dQ9siLEYTqlJtHV_4qNbfxVdsk1ltydQSouwdnxjAM2dpEEyZtBKtdK7G177Rs_-TKCzINwuIpqnzKVcgvPyDXfI0Zs53OiovDm-oFFNlMfpmlTXLg_wnAszycXP/s320/No_wifi_no_app.png&quot; width=&quot;320&quot; /&gt;&lt;/a&gt;&lt;br /&gt;
After closing and reopening browsers it worked as expected and I was shown my offline book which was pretty impressive.&lt;br /&gt;
This is the start of an interesting future for HTML5 readers with fellow Springboard team Publification creating &lt;a href=&quot;http://publification.com/b/moby-dick&quot;&gt;BrowserBooks&lt;/a&gt;&amp;nbsp;which works without having to download extensions and where offline reading is implicit - just like you would have expected.</content><link rel='replies' type='application/atom+xml' href='http://blog.benhall.me.uk/feeds/6571059941289371288/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment/fullpage/post/21967381/6571059941289371288' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/21967381/posts/default/6571059941289371288'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/21967381/posts/default/6571059941289371288'/><link rel='alternate' type='text/html' href='http://blog.benhall.me.uk/2011/08/first-play-with-cloud-based-amazon.html' title='First play with the Cloud-Based Amazon Reader'/><author><name>Ben Hall</name><uri>http://www.blogger.com/profile/17734933641904484310</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='23' height='32' src='//blogger.googleusercontent.com/img/b/R29vZ2xl/AVvXsEiAHZKs2vYlTA1W58oZ3_laZ-JNsUCxXJj__UyIx7TgHEw6DD9nNDr5ML4vvTpu7HbXx0Q5FIWAXyJ2xRsiX97Iu12TNYdSZuMywoqD7Khsbz936TzlIJOBTkDINgB1iYc/s220/n792665715_5219640_7493.jpg'/></author><media:thumbnail xmlns:media="http://search.yahoo.com/mrss/" url="https://blogger.googleusercontent.com/img/b/R29vZ2xl/AVvXsEgZ3_T3Ih957w3_rtcVpSk6uZMI6LOigMklaMgiPMgW0pLu2laC7Ou8K1scBEi4EbnQ2T71qvtc-W-hDl0E-xC2up57Xi94SVQdUUenV4itfpbGRX__jidalOm-Pe8cbkgTvngl/s72-c/Offline_Reading.png" height="72" width="72"/><thr:total>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-21967381.post-8595001733146792796</id><published>2011-07-12T14:11:00.001+00:00</published><updated>2011-07-12T14:12:12.290+00:00</updated><category scheme="http://www.blogger.com/atom/ns#" term="maydayhq"/><category scheme="http://www.blogger.com/atom/ns#" term="meerkatalyst"/><title type='text'>My blog has a few javascript errors... visualise them at MaydayHQ</title><content type='html'>I knew my blog had a few issues, but I had no idea how many!&lt;br /&gt;
&lt;br /&gt;
I&#39;m not the only one. Every day users are encountering bugs and errors with websites that causes them confusion, creates a terrible experience and encourages them to a competitor resulting in companies losing revenue! Companies try and have a friendly &quot;Oops - something went wrong&quot; approach, but it doesn&#39;t hide the problem that the user had a problem.&lt;br /&gt;
&lt;br /&gt;
To make matters worse, companies are unaware of the problems real users are experiencing and instead wait for them to contact customer support - this worked in physical stores, it doesn&#39;t work for the web. With more powerful javascript\HTML5 applications, the buzz around web stores and the wide range of devices pushing the boundaries then problems only going to get worse.&lt;br /&gt;
&lt;br /&gt;
This is why we (&lt;a href=&quot;http://www.meerkatalyst.com/&quot;&gt;Meerkatalyst&lt;/a&gt;) created Mayday (&lt;a href=&quot;http://www.maydayhq.com/&quot;&gt;MaydayHQ.com&lt;/a&gt;). A product designed to capture the problems users experience allowing companies to fix problems&amp;nbsp;before anyone even complains. This means more happy users and as such more revenue. With big plans for the future we&#39;re taking small steps and iterating quick. Currently&amp;nbsp;we&#39;re alerting companies to javascript and in-browser errors and potential reasons for the problem.&lt;br /&gt;
&lt;br /&gt;
You can visualise the errors affecting visitors of my blog at &lt;a href=&quot;http://app.maydayhq.com/demo&quot;&gt;&lt;b&gt;http://app.MaydayHQ.com/demo&lt;/b&gt;&lt;/a&gt; and you can sign up at &lt;a href=&quot;http://www.maydayhq.com/&quot;&gt;&lt;b&gt;http://www.MaydayHQ.com/&lt;/b&gt;&lt;/a&gt;&lt;br /&gt;
&lt;br /&gt;
We&#39;d love to hear your feedback on this, you can reach us at &lt;a href=&quot;http://twitter.com/maydayhq&quot;&gt;@MaydayHQ&lt;/a&gt; or if your in the London \ Cambridge area then we&#39;d love to meetup for a coffee\beer.</content><link rel='replies' type='application/atom+xml' href='http://blog.benhall.me.uk/feeds/8595001733146792796/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment/fullpage/post/21967381/8595001733146792796' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/21967381/posts/default/8595001733146792796'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/21967381/posts/default/8595001733146792796'/><link rel='alternate' type='text/html' href='http://blog.benhall.me.uk/2011/07/my-blog-has-few-javascript-errors.html' title='My blog has a few javascript errors... visualise them at MaydayHQ'/><author><name>Ben Hall</name><uri>http://www.blogger.com/profile/17734933641904484310</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='23' height='32' src='//blogger.googleusercontent.com/img/b/R29vZ2xl/AVvXsEiAHZKs2vYlTA1W58oZ3_laZ-JNsUCxXJj__UyIx7TgHEw6DD9nNDr5ML4vvTpu7HbXx0Q5FIWAXyJ2xRsiX97Iu12TNYdSZuMywoqD7Khsbz936TzlIJOBTkDINgB1iYc/s220/n792665715_5219640_7493.jpg'/></author><thr:total>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-21967381.post-8242454627067363392</id><published>2011-01-18T00:39:00.001+00:00</published><updated>2011-01-18T00:40:20.940+00:00</updated><category scheme="http://www.blogger.com/atom/ns#" term="Hadoop"/><title type='text'>Installing Hadoop 0.21.0 on Windows – Spaces in username gotcha</title><content type='html'>&lt;p&gt;A quick side note about installing Hadoop on Windows. My Windows username is “Ben Hall” – this will be used by hadoop in two places – one being ${user.name} and the other being $USER in shell scripts.&amp;nbsp; &lt;p&gt;As hadoop is cross platform, it doesn’t expect to see spaces in the path names resulting in random errors.  &lt;p&gt;The first one I received was while creating the DFS directory. &lt;pre&gt;11/01/16 17:54:04 WARN common.Util: Path file:///tmp/hadoop-Ben Hall/dfs/name should be specified as a URI in &lt;br&gt;configuration files. Please update hdfs configuration.&lt;br&gt;11/01/16 17:54:04 ERROR common.Util: Error while processing URI: file:///tmp/hadoop-Ben Hall/dfs/name&lt;br&gt;java.io.IOException: The filename, directory name, or volume label syntax is incorrect&lt;br&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; at java.io.WinNTFileSystem.canonicalize0(Native Method)&lt;br&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; at java.io.Win32FileSystem.canonicalize(Win32FileSystem.java:396)&lt;br&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; at java.io.File.getCanonicalPath(File.java:559)&lt;br&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; at java.io.File.getCanonicalFile(File.java:583)&lt;br&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; at org.apache.hadoop.hdfs.server.common.Util.fileAsURI(Util.java:78)&lt;br&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; at org.apache.hadoop.hdfs.server.common.Util.stringAsURI(Util.java:65)&lt;br&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; at org.apache.hadoop.hdfs.server.common.Util.stringCollectionAsURIs(Util.java:91)&lt;br&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; at org.apache.hadoop.hdfs.server.namenode.FSNamesystem.getStorageDirs(FSNamesystem.java:378)&lt;br&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; at org.apache.hadoop.hdfs.server.namenode.FSNamesystem.getNamespaceDirs(FSNamesystem.java:349)&lt;br&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; at org.apache.hadoop.hdfs.server.namenode.NameNode.format(NameNode.java:1223)&lt;br&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; at org.apache.hadoop.hdfs.server.namenode.NameNode.createNameNode(NameNode.java:1348)&lt;br&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; at org.apache.hadoop.hdfs.server.namenode.NameNode.main(NameNode.java:1368)&lt;/pre&gt;
&lt;p&gt;Not the most helpful error message. After some pondering and looking at the hadoop code-base, I realised it was due to the space in my username. To solve the problem I created an override of the default tmp path of the directory without the space. Within core-site.xml, I added the following property node: &lt;pre&gt;&amp;lt;property&amp;gt;&lt;br&gt;&amp;nbsp; &amp;lt;name&amp;gt;hadoop.tmp.dir&amp;lt;/name&amp;gt;&lt;br&gt;&amp;nbsp; &amp;lt;value&amp;gt;/tmp/hadoop-BenHall&amp;lt;/value&amp;gt;&lt;br&gt;&amp;lt;/property&amp;gt; &lt;/pre&gt;
&lt;p&gt;This allowed me to proceed until I hit the following error when starting the nodes: &lt;pre&gt;C:\hadoop\hadoop-0.21.0\/bin/hadoop-daemon.sh: line 111: [: /tmp/hadoop-Ben: binary operator expected&lt;br&gt;C:\hadoop\hadoop-0.21.0\/bin/hadoop-daemon.sh: line 67: [: Hall-namenode-BigBlue7.out: integer expression expected&lt;br&gt;starting namenode, logging to C:\hadoop\hadoop-0.21.0\logs/hadoop-Ben&lt;br&gt;C:\hadoop\hadoop-0.21.0\/bin/hadoop-daemon.sh: line 127: $pid: ambiguous redirect&lt;br&gt;localhost: /cygdrive/c/hadoop/hadoop-0.21.0/bin/hadoop-daemon.sh: line 111: [: /tmp/hadoop-Ben: binary operator expected &lt;/pre&gt;
&lt;p&gt;Again – not an ideal exception. After looking within the hadoop-daemon.sh script, I found a usage of $USER to build up the log output path. Again, this resulted in a space in the path that caused the exception. To fix it, instead of using the $USER variable I hard-coded the value to BENH. 
&lt;p&gt;If you would prefer not to hard-code the value then you could use ‘sed’ to remove spaces dynamically as described here - &lt;a href=&quot;http://mydebian.blogdns.org/?p=132&quot;&gt;http://mydebian.blogdns.org/?p=132&lt;/a&gt;&lt;/p&gt;
&lt;p&gt;After fixing those two errors, I was able to run hadoop without any errors.&lt;/p&gt;  </content><link rel='replies' type='application/atom+xml' href='http://blog.benhall.me.uk/feeds/8242454627067363392/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment/fullpage/post/21967381/8242454627067363392' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/21967381/posts/default/8242454627067363392'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/21967381/posts/default/8242454627067363392'/><link rel='alternate' type='text/html' href='http://blog.benhall.me.uk/2011/01/installing-hadoop-0210-on-windows_4169.html' title='Installing Hadoop 0.21.0 on Windows – Spaces in username gotcha'/><author><name>Ben Hall</name><uri>http://www.blogger.com/profile/17734933641904484310</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='23' height='32' src='//blogger.googleusercontent.com/img/b/R29vZ2xl/AVvXsEiAHZKs2vYlTA1W58oZ3_laZ-JNsUCxXJj__UyIx7TgHEw6DD9nNDr5ML4vvTpu7HbXx0Q5FIWAXyJ2xRsiX97Iu12TNYdSZuMywoqD7Khsbz936TzlIJOBTkDINgB1iYc/s220/n792665715_5219640_7493.jpg'/></author><thr:total>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-21967381.post-8849987387677880349</id><published>2011-01-18T00:31:00.001+00:00</published><updated>2011-01-18T00:31:34.978+00:00</updated><category scheme="http://www.blogger.com/atom/ns#" term="Hadoop"/><title type='text'>Installing Hadoop 0.21.0 on Windows – Installing Hadoop Map\Reduce</title><content type='html'>&lt;p&gt;After configuring your &lt;a href=&quot;http://blog.benhall.me.uk/2011/01/installing-hadoop-0210-on-windows.html&quot; target=&quot;_blank&quot;&gt;SSH server&lt;/a&gt;, you should be ready to install Hadoop core. &lt;/p&gt; &lt;p&gt;&lt;strong&gt;1) Download&lt;/strong&gt;&lt;/p&gt; &lt;p&gt;Firstly, you will need to download the package. If you visit the following site then it will help you find your nearest mirror.&lt;/p&gt; &lt;p&gt;&lt;a href=&quot;http://www.apache.org/dyn/closer.cgi/hadoop/core/&quot;&gt;http://www.apache.org/dyn/closer.cgi/hadoop/core/&lt;/a&gt;&lt;/p&gt; &lt;p&gt;You should then be able to navigate and download Hadoop 0.21.0&lt;/p&gt;&lt;pre&gt;hadoop-0.21.0.tar.gz      17-Aug-2010 06:10   71M  &lt;/pre&gt;
&lt;p&gt;&lt;strong&gt;2) Unpack&lt;/strong&gt;&lt;/p&gt;
&lt;p&gt;Once downloaded, simply unpack the tar into a directory of your choice. As Hadoop is cross platform, ensure you extract it to directory without spaces (not Program Files) as otherwise you may experience random errors. &lt;/p&gt;
&lt;p&gt;The location I picked was C:\hadoop. To extract, run the following command from cygwin:&lt;/p&gt;&lt;pre&gt;$ tar xvfz hadoop-0.21.0.tar.gz&lt;/pre&gt;
&lt;p&gt;&lt;strong&gt;3) Configuration&lt;/strong&gt;&lt;/p&gt;
&lt;p&gt;Once extracted, you need to customise three configuration files - core-site.xml, hdfs-site.xml and mapred-site.xml. I used the settings from the quick start guide below, the settings specify which port different subsystems should run on.&lt;/p&gt;
&lt;p&gt;&lt;a href=&quot;http://hadoop.apache.org/common/docs/current/single_node_setup.html#Configuration&quot;&gt;http://hadoop.apache.org/common/docs/current/single_node_setup.html#Configuration&lt;/a&gt;&lt;/p&gt;
&lt;p&gt;We can now start to test our setup. Personally, with any new tool I attempt to output the version first to check the basic system is happy.&lt;/p&gt;
&lt;p&gt;In this example, execute:&lt;/p&gt;&lt;pre&gt;$ bin/hadoop version&lt;/pre&gt;
&lt;p&gt;In typical fashion, my machine wasn’t configured correctly and I received the following error:&lt;br&gt;Error: JAVA_HOME is not set.&lt;/p&gt;
&lt;p&gt;This indicates that I had to set JAVA_HOME to my JDK installation. &lt;/p&gt;&lt;pre&gt;$ export JAVA_HOME=/cygdrive/c/PROGRA~1/Java/jdk1.6.0_23/ &lt;/pre&gt;
&lt;p&gt;When I tried to output the version again I received a nice java stacktrace – at least it meant something had been executed. To solve this there requires some windows only modifications. &lt;pre&gt;Exception in thread &quot;main&quot; java.lang.NoClassDefFoundError:&lt;br&gt;org/apache/hadoop/util/PlatformName&lt;br&gt;Caused by: java.lang.ClassNotFoundException:&lt;br&gt;org.apache.hadoop.util.PlatformName&lt;br&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; at java.net.URLClassLoader$1.run(Unknown Source)&lt;br&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; at java.security.AccessController.doPrivileged(Native Method)&lt;br&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; at java.net.URLClassLoader.findClass(Unknown Source)&lt;br&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; at java.lang.ClassLoader.loadClass(Unknown Source)&lt;br&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; at sun.misc.Launcher$AppClassLoader.loadClass(Unknown Source)&lt;br&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; at java.lang.ClassLoader.loadClass(Unknown Source)&lt;br&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp; at java.lang.ClassLoader.loadClassInternal(Unknown Source) &lt;/pre&gt;
&lt;p&gt;&lt;strong&gt;4) Modifications for Windows&lt;/strong&gt; 
&lt;p&gt;Personally, this was the most frustrating section however key to solving the above exception. Thankfully I found the answer on this blog post.&lt;/p&gt;
&lt;p&gt;&lt;a href=&quot;http://juliensimon.blogspot.com/2011/01/installing-hadoop-on-windows-cygwin.html&quot;&gt;http://juliensimon.blogspot.com/2011/01/installing-hadoop-on-windows-cygwin.html&lt;/a&gt; 
&lt;p&gt;The problem is that the java classpath can’t find the required Hadoop libs\jars due to the way cygwin handles windows file paths.&lt;/p&gt;
&lt;p&gt;As described in the post, you need to modify hadoop-config.sh. At around line 181, there is an if statement with the comment &quot;&lt;i&gt;# cygwin path translation&lt;/i&gt;&quot;&lt;/p&gt;
&lt;p&gt;Within this block, add &lt;/p&gt;&lt;pre&gt;CLASSPATH=`cygpath -wp &quot;$CLASSPATH&quot;`&lt;/pre&gt;
&lt;p&gt;&lt;em&gt;Pitfall: It won’t have any affect if you don’t add it within the if block. This took me a good hour to work out before finding the post.&lt;/em&gt;&lt;/p&gt;
&lt;p&gt;Attempting the command again, you should hopefully see version output similar to below. &lt;pre&gt;$ hadoop version&lt;br&gt;Hadoop 0.21.0&lt;br&gt;Subversion &lt;a href=&quot;https://svn.apache.org/repos/asf/hadoop/common/branches/branch-0.21&quot;&gt;https://svn.apache.org/repos/asf/hadoop/common/branches/branch-0.21&lt;/a&gt; -r 985326&lt;br&gt;Compiled by tomwhite on Tue Aug 17 01:02:28 EDT 2010&lt;br&gt;From source with checksum a1aeb15b4854808d152989ba76f90fac &lt;/pre&gt;
&lt;p&gt;&lt;strong&gt;5) Starting Hadoop&lt;/strong&gt;&lt;/p&gt;
&lt;p&gt;Now is the time to start running Hadoop. &lt;/p&gt;
&lt;p&gt;Firstly, we need to setup a temporary directory on our harddrive for hadoop to use while running jobs. By default this will be /tmp/hadoop-${user.name} which maps to C:\tmp\hadoop-${your login name}. If you wish use another directory, modify the hadoop.tmp.dir property in your core-site.xml.&lt;/p&gt;
&lt;p&gt;To setup the directory, execute the command.&lt;/p&gt;&lt;pre&gt;$ bin/hadoop namenode -format&lt;/pre&gt;
&lt;p&gt;You can then start hadoop.&lt;/p&gt;&lt;pre&gt;$ ./start-all.sh&lt;/pre&gt;
&lt;p&gt;This will output some information about which nodes have been started. From a developers viewpoint, the most important part will be two new accessible websites. &lt;/p&gt;
&lt;p&gt;HDFS Information &lt;a href=&quot;http://localhost:50070&quot;&gt;http://localhost:50070&lt;/a&gt; – This exposes details about the directory we just created&lt;/p&gt;
&lt;p&gt;JobTracker &lt;a href=&quot;http://localhost:50030&quot;&gt;http://localhost:50030&lt;/a&gt; – This exposes details about any running or finished jobs&lt;/p&gt;
&lt;p&gt;That’s it. Hadoop is now ready to start executing jobs which I’ll discuss in my next post.&lt;/p&gt;  </content><link rel='replies' type='application/atom+xml' href='http://blog.benhall.me.uk/feeds/8849987387677880349/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment/fullpage/post/21967381/8849987387677880349' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/21967381/posts/default/8849987387677880349'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/21967381/posts/default/8849987387677880349'/><link rel='alternate' type='text/html' href='http://blog.benhall.me.uk/2011/01/installing-hadoop-0210-on-windows_18.html' title='Installing Hadoop 0.21.0 on Windows – Installing Hadoop Map\Reduce'/><author><name>Ben Hall</name><uri>http://www.blogger.com/profile/17734933641904484310</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='23' height='32' src='//blogger.googleusercontent.com/img/b/R29vZ2xl/AVvXsEiAHZKs2vYlTA1W58oZ3_laZ-JNsUCxXJj__UyIx7TgHEw6DD9nNDr5ML4vvTpu7HbXx0Q5FIWAXyJ2xRsiX97Iu12TNYdSZuMywoqD7Khsbz936TzlIJOBTkDINgB1iYc/s220/n792665715_5219640_7493.jpg'/></author><thr:total>0</thr:total></entry></feed>