<?xml version="1.0" encoding="UTF-8"?>
<?xml-stylesheet type="text/xsl" media="screen" href="/~d/styles/rss2full.xsl"?><?xml-stylesheet type="text/css" media="screen" href="http://feeds.feedburner.com/~d/styles/itemcontent.css"?><rss xmlns:content="http://purl.org/rss/1.0/modules/content/" xmlns:wfw="http://wellformedweb.org/CommentAPI/" xmlns:dc="http://purl.org/dc/elements/1.1/" xmlns:atom="http://www.w3.org/2005/Atom" xmlns:sy="http://purl.org/rss/1.0/modules/syndication/" xmlns:slash="http://purl.org/rss/1.0/modules/slash/" xmlns:feedburner="http://rssnamespace.org/feedburner/ext/1.0" version="2.0">

<channel>
	<title>[Don write:blog];</title>
	
	<link>http://blog.donwilson.net</link>
	<description>Confessions of an addicted coder</description>
	<lastBuildDate>Wed, 07 Nov 2012 23:44:51 +0000</lastBuildDate>
	<language>en-US</language>
	<sy:updatePeriod>hourly</sy:updatePeriod>
	<sy:updateFrequency>1</sy:updateFrequency>
	<generator>http://wordpress.org/?v=3.5.1</generator>
		<atom10:link xmlns:atom10="http://www.w3.org/2005/Atom" rel="self" type="application/rss+xml" href="http://feeds.feedburner.com/donwriteblog" /><feedburner:info uri="donwriteblog" /><atom10:link xmlns:atom10="http://www.w3.org/2005/Atom" rel="hub" href="http://pubsubhubbub.appspot.com/" /><feedburner:emailServiceId>donwriteblog</feedburner:emailServiceId><feedburner:feedburnerHostname>http://feedburner.google.com</feedburner:feedburnerHostname><item>
		<title>Blackbird! – A Game for Rook fans on iPhone, iPad, and iPod Touch</title>
		<link>http://feedproxy.google.com/~r/donwriteblog/~3/NoMViY0tjuE/</link>
		<comments>http://blog.donwilson.net/2012/10/blackbird-a-game-for-rook-fans-on-iphone-ipad-and-ipod-touch/#comments</comments>
		<pubDate>Wed, 31 Oct 2012 04:55:57 +0000</pubDate>
		<dc:creator>dontangg</dc:creator>
				<category><![CDATA[Programming]]></category>
		<category><![CDATA[Projects]]></category>
		<category><![CDATA[iOS]]></category>
		<category><![CDATA[iPhone]]></category>
		<category><![CDATA[Objective-C]]></category>

		<guid isPermaLink="false">http://blog.donwilson.net/?p=405</guid>
		<description><![CDATA[* I am not affiliated with Hasbro! It has been a month now since my iOS card game app based on Rook, Blackbird, has been approved in the App Store. It has been a blast! It is definitely the funnest (&#8230;)</p><p><a href="http://blog.donwilson.net/2012/10/blackbird-a-game-for-rook-fans-on-iphone-ipad-and-ipod-touch/">Read the rest of this entry &#187;</a></p>]]></description>
				<content:encoded><![CDATA[<p><small>* I am not affiliated with Hasbro!</small></p>
<p>It has been a month now since my iOS card game app based on Rook, <a href='https://itunes.apple.com/us/app/blackbird!/id563960217?ls=1&#038;mt=8'>Blackbird</a>, has been approved in the App Store. It has been a blast! It is definitely the funnest project that I have worked on. I think that is mainly due to the fact that I did it all myself and the App Store is a big market. Well, I can&#8217;t really say that because I&#8217;ve had lots of input and help with testing from friends and family &#8211; mostly my dad who is a big Rook fan. I thought I&#8217;d just write up a quick post on some things I&#8217;ve learned, and throw in some app statistics.</p>
<p><span id="more-405"></span></p>
<h3>Some things I have learned</h3>
<p>I chose to write an iOS app simply because I have an iPhone and most of my family have iPhones.</p>
<p>I didn&#8217;t use a cross-platform developer tool like Titanium that would allow me to write code once and deploy to iOS and Android. This was a very hard decision for me, but I&#8217;m glad I went the XCode/Objective C route. Here are my reasons: (Whenever I say, &#8220;Titanium&#8221;, I really mean any project like it. They all work very similarly.)</p>
<ul>
<li>The Objective C language is really growing on me. It&#8217;s very different at first and has some concepts that are unlike any language that I&#8217;d learned before. But I really like it now. So I&#8217;m glad I took the time to learn.</li>
<li>I have a computer playing AI that I want to be as fast as possible. Even though they translate the JavaScript into native code, I can write native code that performs faster for my specific tasks than Titanium can. I feel comfortable that when I need to work on performance, I can get every inch of performance possible.</li>
<li>I have a problem feeling restricted to the currently implemented features. I worry about running into a situation where I want to use a feature that is supported by the platform, but not implemented by Titanium. This may be an irrational fear, but I still have it.</li>
<li>I have recently talked to people who have worked on Titanium projects and they have told me that they both love it and hate it. They say that some bugs are really hard to track down because you&#8217;re not sure if the bug is in your code or theirs. They also say that you still end up writing a lot of platform-specific code. You also have to pay for their nicer versions and you have to write modules to support native iOS features that aren&#8217;t yet implemented by Titanium.</li>
</ul>
<p>The up side of writing in a language I&#8217;m already familiar with (JavaScript) and deploying to multiple platforms at the same time just isn&#8217;t worth it <strong>to me</strong>.</p>
<p>When I released the app, it had relatively few features. I knew that there were several things that would be in high demand, but I released it without them anyways. I&#8217;m really glad I made that decision. The feedback has poured in and it has definitely steered me in a different direction that I would have taken on my own.</p>
<p>I haven&#8217;t done any marketing yet. I&#8217;ll be interested to see if I can get some app review sites to review my app and what effect that will have. I expect that a multi-player mode and a universal app will also have a big impact. So, I&#8217;m excited for the future!</p>
<h3>Statistics</h3>
<p>Here are several statistics so far:</p>
<p>Initially approved for sale in the App Store: Sept 29, 2012<br />
Total downloads: 561<br />
Updates approved: 3<br />
App store rejections: 0<br />
Most sessions in 1 day: 979<br />
Median session length: 6.3 mins<br />
Total time spent in app yesterday: 5 days 14 hours<br />
iOS versions: 88.9% iOS 6.0, 10% iOS 5.1.1, 1% iOS 5.1 (my app requires iOS 5.1)<br />
Users with a device that cannot upgrade to iOS 6: 1%<br />
Countries of users: USA, Canada, Japan, Australia, Hong Kong, Kuwait</p>
<img src="http://feeds.feedburner.com/~r/donwriteblog/~4/NoMViY0tjuE" height="1" width="1"/>]]></content:encoded>
			<wfw:commentRss>http://blog.donwilson.net/2012/10/blackbird-a-game-for-rook-fans-on-iphone-ipad-and-ipod-touch/feed/</wfw:commentRss>
		<slash:comments>24</slash:comments>
		<feedburner:origLink>http://blog.donwilson.net/2012/10/blackbird-a-game-for-rook-fans-on-iphone-ipad-and-ipod-touch/</feedburner:origLink></item>
		<item>
		<title>How to Setup Reactive Cocoa (RAC) for Use in Your iOS App</title>
		<link>http://feedproxy.google.com/~r/donwriteblog/~3/WkpUEoS54R0/</link>
		<comments>http://blog.donwilson.net/2012/06/how-to-setup-reactive-rac-cocoa-for-use-in-your-ios-app/#comments</comments>
		<pubDate>Thu, 28 Jun 2012 06:28:03 +0000</pubDate>
		<dc:creator>dontangg</dc:creator>
				<category><![CDATA[Programming]]></category>
		<category><![CDATA[Objective-C]]></category>
		<category><![CDATA[RAC]]></category>
		<category><![CDATA[ReactiveCocoa]]></category>

		<guid isPermaLink="false">http://blog.donwilson.net/?p=356</guid>
		<description><![CDATA[I am writing an iOS app and I found GitHub&#8217;s Reactive Cocoa very helpful. There isn&#8217;t any documentation on the ReactiveCocoa README on how to install it and there are many ways. I tried CocoaPods but it added and changed (&#8230;)</p><p><a href="http://blog.donwilson.net/2012/06/how-to-setup-reactive-rac-cocoa-for-use-in-your-ios-app/">Read the rest of this entry &#187;</a></p>]]></description>
				<content:encoded><![CDATA[<p>I am writing an iOS app and I found <a href="https://github.com/github/ReactiveCocoa" target="_blank">GitHub&#8217;s Reactive Cocoa</a> very helpful.</p>
<p>There isn&#8217;t any documentation on the ReactiveCocoa README on how to install it and there are many ways. I tried <a href="http://cocoapods.org/" target="_blank">CocoaPods</a> but it added and changed a whole bunch of stuff. It made me uncomfortable, and I&#8217;m the kind of person that likes to know exactly what&#8217;s going on, so I decided to do it on my own. I did it the same way the RACiOSDemo project was setup.</p>
<p><span id="more-356"></span><br />
<h4>Create a Git submodule</h4>
<p>Create a folder called external in the project&#8217;s root folder. Then, run this to add the submodule:</p>
<p><code>
<pre>
$ git submodule add https://github.com/github/ReactiveCocoa external/ReactiveCocoa
$ git add .gitmodules external/ReactiveCocoa
$ git commit -m "Add ReactiveCocoa as a submodule"
</pre>
<p></code></p>
<p>If you&#8217;re not familiar with submodules, submodules are simply a way of embedding a git repository inside another. If you&#8217;re still curious, I recommend reading the <a href="http://git-scm.com/book/en/Git-Tools-Submodules" target="_blank">Git book&#8217;s chapter on submodules</a>.</p>
<p>Now, anytime you clone your repository, you&#8217;ll also need to run these two commands to set up the submodule again:</p>
<pre>$ git submodule init
$ git submodule update</pre>
<h4>Setup ReactiveCocoa correctly in your project</h4>
<p>Next we need to get the project to appear and build inside our project. In your XCode project, right-click on the Frameworks folder and choose &#8220;Add Files to [project]&#8230;&#8221;. Navigate to external/ReactiveCocoa/ReactiveCocoaFramework and choose ReactiveCocoa.xcodeproj.</p>
<p>Now we need to setup the our project&#8217;s main target to link to the framework. Click on your project in the project explorer. Then, click on your main target and make sure you&#8217;re on the Summary tab. Scroll down to the &#8220;Linked Frameworks and Libraries&#8221; section. Click the plus and add libReactiveCocoa-iOS.a.</p>
<p><img class="size-full wp-image-364 alignnone" title="Linking to libReactiveCocoa-iOS.a" src="http://blog.donwilson.net/wp-content/uploads/2012/06/Screen-Shot-2012-06-28-at-12.18.24-AM.png" alt="" width="470" height="115" /></p>
<p>Apparently, for now, we also need to add a linker switch for it to compile the ReactiveCocoa stuff correctly. Go to the Build Settings tab now and scroll down to the &#8220;Linking&#8221; section. Find the &#8220;Other Linker Flags&#8221; setting and double-click in the field to the right. Add the -ObjC flag and the -all_load flags.</p>
<p><a href="http://blog.donwilson.net/wp-content/uploads/2012/06/Screen-Shot-2012-06-28-at-12.13.19-AM.png"><img class="alignnone size-full wp-image-366" title="Adding linker switch for ReactiveCocoa" src="http://blog.donwilson.net/wp-content/uploads/2012/06/Screen-Shot-2012-06-28-at-12.13.19-AM.png" alt="" width="553" height="299" /></a></p>
<p>The last thing we need to do is tell XCode where to look for the framework and header files. Still in the Build Settings tab, scroll down to the &#8220;Search Paths&#8221; section. Find the &#8220;Framework Search Paths&#8221; and enter the value, &#8220;$(PROJECT_DIR)/external/ReactiveCocoa/ReactiveCocoaFramework&#8221;. Then put the same value in for the &#8220;Header Search Path&#8221;.</p>
<p>That&#8217;s it. Now, you can happily use Reactive Cocoa all you want!</p>
<img src="http://feeds.feedburner.com/~r/donwriteblog/~4/WkpUEoS54R0" height="1" width="1"/>]]></content:encoded>
			<wfw:commentRss>http://blog.donwilson.net/2012/06/how-to-setup-reactive-rac-cocoa-for-use-in-your-ios-app/feed/</wfw:commentRss>
		<slash:comments>0</slash:comments>
		<feedburner:origLink>http://blog.donwilson.net/2012/06/how-to-setup-reactive-rac-cocoa-for-use-in-your-ios-app/</feedburner:origLink></item>
		<item>
		<title>Deploying A Rails App To Rackspace Cloud Servers On Ubuntu Using Nginx and Unicorn</title>
		<link>http://feedproxy.google.com/~r/donwriteblog/~3/VIwT1leYkZ0/</link>
		<comments>http://blog.donwilson.net/2012/04/deploying-a-rails-app-to-rackspace-cloud-servers-using-nginx-and-unicorn/#comments</comments>
		<pubDate>Thu, 05 Apr 2012 01:00:02 +0000</pubDate>
		<dc:creator>dontangg</dc:creator>
				<category><![CDATA[Programming]]></category>
		<category><![CDATA[capistrano]]></category>
		<category><![CDATA[deployment]]></category>
		<category><![CDATA[envelopes]]></category>
		<category><![CDATA[nginx]]></category>
		<category><![CDATA[Rails]]></category>
		<category><![CDATA[Ruby]]></category>
		<category><![CDATA[unicorn]]></category>

		<guid isPermaLink="false">http://blog.donwilson.net/?p=283</guid>
		<description><![CDATA[I recently setup a Rails server on Ubuntu using Nginx and Unicorn and a database running on the same server using Postgres. I also used rbenv and ruby-build for ruby. I had to look up a lot of information to (&#8230;)</p><p><a href="http://blog.donwilson.net/2012/04/deploying-a-rails-app-to-rackspace-cloud-servers-using-nginx-and-unicorn/">Read the rest of this entry &#187;</a></p>]]></description>
				<content:encoded><![CDATA[<p>I recently setup a Rails server on Ubuntu using Nginx and Unicorn and a database running on the same server using Postgres. I also used rbenv and ruby-build for ruby. I had to look up a lot of information to get this all working. I just wanted to consolidate everything I did into one place. Hopefully, all this can help someone else.</p>
<p><span id="more-283"></span><br />
Here are some links to the different parts of this post:</p>
<ul>
<li><a href="http://blog.donwilson.net/2012/04/deploying-a-rails-app-to-rackspace-cloud-servers-using-nginx-and-unicorn/#why-these">Why use these technologies?</a></li>
<li><a href="http://blog.donwilson.net/2012/04/deploying-a-rails-app-to-rackspace-cloud-servers-using-nginx-and-unicorn/?page=2">The server</a></li>
<li><a href="http://blog.donwilson.net/2012/04/deploying-a-rails-app-to-rackspace-cloud-servers-using-nginx-and-unicorn/?page=3">PostgreSQL</a></li>
<li><a href="http://blog.donwilson.net/2012/04/deploying-a-rails-app-to-rackspace-cloud-servers-using-nginx-and-unicorn/?page=4">Nginx</a></li>
<li><a href="http://blog.donwilson.net/2012/04/deploying-a-rails-app-to-rackspace-cloud-servers-using-nginx-and-unicorn/?page=5">Unicorn</a></li>
<li><a href="http://blog.donwilson.net/2012/04/deploying-a-rails-app-to-rackspace-cloud-servers-using-nginx-and-unicorn/?page=6">Capistrano</a></li>
</ul>
<p>Here are some resources I used to get everything setup the way I wanted:</p>
<ul>
<li><a href="http://sirupsen.com/setting-up-unicorn-with-nginx/">Setting up Unicorn with Nginx</a></li>
<li><a href="https://help.ubuntu.com/community/PostgreSQL">Setting up PostgreSQL on Ubuntu</a></li>
<li><a href="http://ariejan.net/2011/09/14/lighting-fast-zero-downtime-deployments-with-git-capistrano-nginx-and-unicorn">Lighting fast, zero-downtime deployments with git, capistrano, nginx and Unicorn</a></li>
</ul>
<p>I took my approach from many different places and I&#8217;ll explain why I did what I did.</p>
<p><strong>Update</strong> &#8211; I have since watched a few Railscasts that are very well done and explain most of the same concepts. There are several things that he recommends doing that I will definitely do. He is charging money to see those episodes ($9/month), so I would feel a little guilty posting what I learned here.</p>
<ul>
<li><a href="http://railscasts.com/episodes/335-deploying-to-a-vps">Deploying To A VPS</a></li>
<li><a href="http://railscasts.com/episodes/293-nginx-unicorn">Nginx &#038; Unicorn</a></li>
<li><a href="http://railscasts.com/episodes/337-capistrano-recipes">Capistrano Recipes</a></li>
</ul>
<h3 id='why-these'>Why use these technologies?</h3>
<h4>Hosting</h4>
<p>Originally, I wanted to host my website on <strong>Heroku</strong>. Heroku is easy, awesome, and really simple. One web dyno is free and it can scale really easily. For the foreseeable future, however, I will have very low traffic and I want it to be as cheap as possible.</p>
<p>My problem with Heroku came when I realized that I needed more than 5MB of database space. The next tier up gives me 20GB and costs $15/month. This is way more space than I need and costs a lot more than I want to pay.</p>
<p>So, I started looking at VPS hosting since I can get a cheap VPS and have more than 5MB of space for my database, plus I can use it to run jobs if I want, etc. I looked at the cheapest offered solutions at Linode, Dreamhhost, MediaTemple, Amazon, and Rackspace. Rackspace beats them all with 256MB of RAM and 10GB Disk for $11/month + $0.18/GB of bandwidth. I highly doubt that I&#8217;ll even use 1GB of bandwidth. Plus, if I do need to scale, it will be really easy to do it with Rackspace Cloud Servers.</p>
<h4>Web Framework</h4>
<p>Honestly, my main reason for doing my site in Rails is because I love Ruby and Rails is fun to work in.</p>
<h4>Http Server</h4>
<p>My reasons are better stated by others:</p>
<ul>
<li><a href="http://cmelbye.github.com/2009/10/04/thin-vs-unicorn.html">Thin vs. Unicorn</a></li>
<li><a href="https://github.com/blog/517-unicorn">Unicorn!</a></li>
<li><a href="http://labs.revelationglobal.com/2009/10/06/mongrel_passenger_unicorn.html">Mongrel vs. Passenger vs. Unicorn</a></li>
</ul>
<p>Since this is for a low traffic site, I went on the word of others. If I was expecting a lot of traffic, I probably would have done more research and some of my own benchmarks. That said, I do feel pretty confident in this setup even though I didn&#8217;t do that. Let&#8217;s get started!</p>
<img src="http://feeds.feedburner.com/~r/donwriteblog/~4/VIwT1leYkZ0" height="1" width="1"/>]]></content:encoded>
			<wfw:commentRss>http://blog.donwilson.net/2012/04/deploying-a-rails-app-to-rackspace-cloud-servers-using-nginx-and-unicorn/feed/</wfw:commentRss>
		<slash:comments>9</slash:comments>
		<feedburner:origLink>http://blog.donwilson.net/2012/04/deploying-a-rails-app-to-rackspace-cloud-servers-using-nginx-and-unicorn/</feedburner:origLink></item>
		<item>
		<title>A Simple Site To Automate Sending Texts/Emails</title>
		<link>http://feedproxy.google.com/~r/donwriteblog/~3/HB5rVnqNVKI/</link>
		<comments>http://blog.donwilson.net/2012/03/a-simple-site-to-automate-sending-textsemails/#comments</comments>
		<pubDate>Fri, 16 Mar 2012 02:00:39 +0000</pubDate>
		<dc:creator>dontangg</dc:creator>
				<category><![CDATA[Productivity]]></category>
		<category><![CDATA[Programming]]></category>
		<category><![CDATA[Email]]></category>
		<category><![CDATA[Google API]]></category>
		<category><![CDATA[Ruby]]></category>
		<category><![CDATA[Sinatra]]></category>
		<category><![CDATA[SMS]]></category>

		<guid isPermaLink="false">http://blog.donwilson.net/?p=259</guid>
		<description><![CDATA[I&#8217;m often thinking about things that I could code up that would make tasks simpler.  Generally, that means that I spend a lot of time up front to write a tool that automates a task.  Then, I slowly get that (&#8230;)</p><p><a href="http://blog.donwilson.net/2012/03/a-simple-site-to-automate-sending-textsemails/">Read the rest of this entry &#187;</a></p>]]></description>
				<content:encoded><![CDATA[<p>I&#8217;m often thinking about things that I could code up that would make tasks simpler.  Generally, that means that I spend a lot of time up front to write a tool that automates a task.  Then, I slowly get that time back over time using the tool.  But, it&#8217;s fun anyways. So, this is what I decided to automate.<span id="more-259"></span></p>
<h2>Justification</h2>
<p><a title="My Mormon Profile" href="http://mormon.org/me/2ZXC/" target="_blank">I am a Mormon.</a>  No one is paid to do anything at my church.  So, we have to setup all the chairs for everyone every Sunday.  We have split into different groups so that we really only have to come setup chairs once every month.  I am in charge of reminding my group that it&#8217;s our turn.  These groups change pretty often with people moving in and out, so we keep the list of groups in a Google Spreadsheet.  I often forget that I need to remind everyone until it&#8217;s inconvenient for me.  I have often looked up the list in the Google spreadsheet on my phone and copied them, 5 at a time, into Google Voice to send texts.  It feels painful.</p>
<h2>Solution</h2>
<p>To make this easier for me, I decided to write a simple website that would read the data from the Google spreadsheet for me. Then, I could type type in my message and click &#8220;Send SMS&#8221; and be done.  I was able to do this in about 4 days in my spare time, but there are some caveats.  I&#8217;m going to give a brief tour of this tiny little site.  I&#8217;m not going to talk about any of the code, but it&#8217;s up on GitHub.  If you&#8217;re interested, I used <a title="Sinatra" href="http://www.sinatrarb.com/" target="_blank">Sinatra</a> with <a title="Haml" href="http://haml-lang.com/" target="_blank">Haml</a>, the <a title="Google Spreadsheet API" href="https://developers.google.com/google-apps/spreadsheets/" target="_blank">Google Spreadsheet API</a> via the <a title="Google API Ruby Client" href="http://code.google.com/p/google-api-ruby-client" target="_blank">Google API Ruby client</a> and <a title="Faraday" href="https://github.com/technoweenie/faraday" target="_blank">Faraday</a>, <a title="Moonshado SMS" href="https://addons.heroku.com/moonshadosms" target="_blank">Moonshado SMS</a>, <a title="MongoDB" href="http://www.mongodb.org/" target="_blank">MongoDB</a> with <a title="Mongoid" href="http://mongoid.org/" target="_blank">Mongoid</a> on <a title="MongoLab" href="https://mongolab.com/home" target="_blank">MongoLab</a>, the <a title="Twitter Bootstrap" href="http://twitter.github.com/bootstrap/" target="_blank">Twitter Bootstrap</a>, and <a title="Heroku" href="http://www.heroku.com/" target="_blank">Heroku</a>.  It was all free!!!  If you want my code, <a title="EQ Automator on GitHub" href="https://github.com/dontangg/eq_automator" target="_blank">go here</a>.</p>
<h2>Short Tour</h2>
<p>The home page is just a simple page with a random quote about time that changes every time you come to the page and a link to the contact page.  I&#8217;m guessing that I might add more tools like this in the future.</p>
<p><a href="http://blog.donwilson.net/wp-content/uploads/2012/03/home3.png"><img class="aligncenter size-full wp-image-272" title="home" src="http://blog.donwilson.net/wp-content/uploads/2012/03/home3.png" alt="" width="1022" height="378" /></a></p>
<p>When you click on the &#8220;Contact the quroum&#8221; link it takes you to a Google page where it tells you that I&#8217;m asking for permission to use your spreadsheets.  If you give permission, it takes you to the only other page in the app, the contact page.  You can select from a bunch of preset groups of contacts or you can manually click on the names to add them or remove them from the list.  You can see who has an email or phone number in the spreadsheet with the icons next to each name.  Then, you type in your message and click the SMS button if you want it to send a text message.  Or, click the Email button if you want to send an email.  The site responds to your browser size too.  So, if you are on a mobile phone, it&#8217;s still pretty usable.  Pretty simple.  (I removed a bunch of names and changed the names in the screenshot below).</p>
<p><a href="http://blog.donwilson.net/wp-content/uploads/2012/03/contact.png"><img class="aligncenter size-full wp-image-273" title="contact" src="http://blog.donwilson.net/wp-content/uploads/2012/03/contact.png" alt="" width="1022" height="551" /></a></p>
<p>One caveat is that right now, I can only send 17 text message a month for free.  I have 19 people in my group.  Also, when it sends the text, it adds &#8220;Msg&amp;data rates may apply txt STOP to opt-out.&#8221;  That&#8217;s kind of crappy.  Also, if I&#8217;m asking a question and they want to reply, their reply won&#8217;t make it to my phone.  So, I&#8217;m thinking of changing from using MoonShado SMS to Twilio.  With Twilio it won&#8217;t be free, but I&#8217;ll get everything that I want for about $1.17/month.  I&#8217;m still deciding if it&#8217;s worth it to me.  Either way it was a fun project and I&#8217;ll still use it!</p>
<img src="http://feeds.feedburner.com/~r/donwriteblog/~4/HB5rVnqNVKI" height="1" width="1"/>]]></content:encoded>
			<wfw:commentRss>http://blog.donwilson.net/2012/03/a-simple-site-to-automate-sending-textsemails/feed/</wfw:commentRss>
		<slash:comments>0</slash:comments>
		<feedburner:origLink>http://blog.donwilson.net/2012/03/a-simple-site-to-automate-sending-textsemails/</feedburner:origLink></item>
		<item>
		<title>Constructing A Less Than Simple Query With Rails And ARel</title>
		<link>http://feedproxy.google.com/~r/donwriteblog/~3/npoRx-pCIY0/</link>
		<comments>http://blog.donwilson.net/2011/11/constructing-a-less-than-simple-query-with-rails-and-arel/#comments</comments>
		<pubDate>Sun, 27 Nov 2011 07:38:31 +0000</pubDate>
		<dc:creator>dontangg</dc:creator>
				<category><![CDATA[Programming]]></category>
		<category><![CDATA[Rails]]></category>
		<category><![CDATA[Ruby]]></category>

		<guid isPermaLink="false">http://blog.donwilson.net/?p=246</guid>
		<description><![CDATA[I say the query is less than simple because it&#8217;s not really complicated either.  In my little application, I really only have one query that is like this and this is the one.  This is the query that I wanted (&#8230;)</p><p><a href="http://blog.donwilson.net/2011/11/constructing-a-less-than-simple-query-with-rails-and-arel/">Read the rest of this entry &#187;</a></p>]]></description>
				<content:encoded><![CDATA[<p>I say the query is less than simple because it&#8217;s not really complicated either.  In my little application, I really only have one query that is like this and this is the one.  This is the query that I wanted to run:</p>
<pre class="brush: sql; title: ; notranslate">
SELECT &quot;envelopes&quot;.*, COALESCE(SUM(&quot;transactions&quot;.&quot;amount&quot;), 0) AS total_amount
FROM &quot;envelopes&quot; LEFT OUTER JOIN &quot;transactions&quot; ON &quot;envelopes&quot;.&quot;id&quot; = &quot;transactions&quot;.&quot;envelope_id&quot;
WHERE &quot;envelopes&quot;.&quot;user_id&quot; = 3
GROUP BY &quot;envelopes&quot;.&quot;id&quot;, &quot;envelopes&quot;.&quot;name&quot;, &quot;envelopes&quot;.&quot;user_id&quot;, &quot;envelopes&quot;.&quot;income&quot;, &quot;envelopes&quot;.&quot;unassigned&quot;, &quot;envelopes&quot;.&quot;parent_envelope_id&quot;, &quot;envelopes&quot;.&quot;expense&quot;, &quot;envelopes&quot;.&quot;created_at&quot;, &quot;envelopes&quot;.&quot;updated_at&quot;
ORDER BY &quot;envelopes&quot;.&quot;name&quot;
</pre>
<p><span id="more-246"></span></p>
<p>Don&#8217;t try to read that. It looks more complicated than it is because it&#8217;s long. In my application, users have envelopes and those envelopes have transactions and transactions have a cash amount. Basically, I&#8217;m getting all the envelopes owned by a user and the total amount for each envelope (a SUM of all the amounts of all the transactions in those envelopes). This query is definitely more complicated than the typical query, but as far as SQL goes, it&#8217;s still pretty simple. Here were my priorities for this:</p>
<ul>
<li>One query that gets the job done. Not more than one query.</li>
<li>Use ActiveRecord to consume the query. I still wanted to work with Envelope objects even though I also wanted the total.</li>
<li>No extensive use of strings because I use SQLite3 for development and Postgres for production. There are differences in syntax (quoting, etc.) that I don&#8217;t want to worry about.</li>
</ul>
<p>My first attempt was just creating a SQL string to see if I could just use the <code>find_by_sql</code> method to get all the data back and still access the total.</p>
<pre class="brush: ruby; title: ; notranslate">
sql = 'SELECT &quot;envelopes&quot;.*, COALESCE(SUM(&quot;transactions&quot;.&quot;amount&quot;), 0) AS total_amount FROM &quot;envelopes&quot; LEFT OUTER JOIN &quot;transactions&quot; ON &quot;envelopes&quot;.&quot;id&quot; = &quot;transactions&quot;.&quot;envelope_id&quot; WHERE &quot;envelopes&quot;.&quot;user_id&quot; = 3 GROUP BY &quot;envelopes&quot;.&quot;id&quot;, &quot;envelopes&quot;.&quot;name&quot;, &quot;envelopes&quot;.&quot;user_id&quot;, &quot;envelopes&quot;.&quot;income&quot;, &quot;envelopes&quot;.&quot;unassigned&quot;, &quot;envelopes&quot;.&quot;parent_envelope_id&quot;, &quot;envelopes&quot;.&quot;expense&quot;, &quot;envelopes&quot;.&quot;created_at&quot;, &quot;envelopes&quot;.&quot;updated_at&quot; ORDER BY &quot;envelopes&quot;.&quot;name&quot;'
envelopes = Envelope.find_by_sql(sql)
</pre>
<p>This worked great. It turns out that all the columns returned were accessible. For example, when I have an envelope populated with data from this query, I can just say <code>envelope.total_amount</code> to get the value and it doesn&#8217;t do any other queries even though <code>total_amount</code> isn&#8217;t a column in the envelopes table. To make this access even nicer, I added a method to my Envelope class.</p>
<pre class="brush: ruby; title: ; notranslate">
def total_amount
  @total_amount ||= read_attribute(:total_amount) || transactions.sum(:amount)
end
</pre>
<p><code>read_attribute</code> is what is called behind the scenes whenever you access your data. I call that since it won&#8217;t get to <code>method_missing</code> anymore when I try to access <code>total_amount</code>. If that value wasn&#8217;t provided in the query that populated this envelope object, then I get it by summing all the transactions&#8217; amounts. Either way, I memoize the value in an instance variable. If the instance variable is set, it will return it&#8217;s value before doing anything else. Using a tip found on <a href='http://weblog.jamisbuck.org/2007/1/8/watching-activerecord-do-it-s-thing'>Jamis Buck&#8217;s blog</a> was very helpful in testing this to make sure it was working. To see all the SQL queries that are run, you can just run <code>ActiveRecord::Base.logger = Logger.new(STDOUT)</code> in the Rails console.</p>
<p>This solution is nice because it solves the first two concerns I had. However, it isn&#8217;t very portable. The whole query is just a string. So I looked through the Rails documentation to see if it was possible to build this query just using the Active Record Query Interface. The things that I was having a hard time figuring out how to do was getting all of the envelopes columns while summing the transactions as well as getting an outer join in the query. If there aren&#8217;t any transactions, I still want the envelope to return (inner join doesn&#8217;t work). I could get it to do an outer join if I used the <code>includes</code> method and I put something in the <code>where</code> that required the included table. Anyways&#8230; I decided to just build the SQL string using ARel and just plop it into the <code>find_by_sql</code> method. After a lot of digging through ARel documentation and looking through the source code, I finally found a way to do it. Here it is:</p>
<pre class="brush: ruby; title: ; notranslate">
et = Envelope.arel_table
tt = Transaction.arel_table

envelopes_columns = Envelope.column_names.map {|column_name| et[column_name.to_sym] }
    
sum_function = Arel::Nodes::NamedFunction.new('SUM', [tt[:amount]])
aggregation = Arel::Nodes::NamedFunction.new('COALESCE', [sum_function, 0], 'total_amount')

sql = et.project(et[Arel.star], aggregation)
        .join(tt, Arel::Nodes::OuterJoin).on(et[:id].eq(tt[:envelope_id]))
        .where(et[:user_id].eq(user_id))
        .group(*envelopes_columns)
        .order(et[:name]).to_sql

Envelope.find_by_sql(sql)
</pre>
<p>There are a couple of tricks that I learned worth mentioning. The first one that appears in the code above is that you can get ARel to do any function supported in databases even if ARel doesn&#8217;t natively understand it. Just use the NamedFunction class and pass in all the arguments for that function as an array. The 3rd argument is an optional alias. Even though <code>SUM()</code> is natively supported, I had to add it this way because it puts an alias in the wrong spot if I used the native way since I want the <code>SUM()</code> inside the <code>COALESCE()</code>. I want the <code>COALESCE()</code> because if it returns null, then I&#8217;ll do another database query in my <code>total_amount</code> function.</p>
<p>The next trick is that you can do <code>et[Arel.star]</code> to generate <code>"Envelopes".*</code>. This is nice because the Envelopes table is quoted in the database-specific way (for sqlite here) and the splat is not quoted.</p>
<p>The last thing that if you want to use an outer join, just pass in the join class you want to use as a second parameter to the <code>join</code> method&#8230; easy!</p>
<p>That&#8217;s it. This worked. (If you&#8217;re wondering about the <code>*envelopes_columns</code> part, you need to go through <a href='http://tryruby.org'>Try Ruby</a>).</p>
<p>This actually met all of my initial priorities, but something didn&#8217;t sit right with me. I didn&#8217;t like how this query was not chainable like all of the other ActiveRecord queries. I can&#8217;t use any of my other scopes with it. So, I went back to the ActiveRecord Query Interface and this time, I dug into the documentation more and looked through some Rails code. I found a way to make it all work using a combination of ActiveRecord and ARel.</p>
<pre class="brush: ruby; title: ; notranslate">
et = Envelope.arel_table
tt = Transaction.arel_table
    
envelopes_columns = Envelope.column_names.map {|column_name| et[column_name.to_sym] }
    
sum_function = Arel::Nodes::NamedFunction.new('SUM', [tt[:amount]])
aggregation = Arel::Nodes::NamedFunction.new('COALESCE', [sum_function, 0], 'total_amount')
    
select([et[Arel.star], aggregation])
  .joins(Arel::Nodes::OuterJoin.new(tt, Arel::Nodes::On.new(et[:id].eq(tt[:envelope_id]))))
  .group(envelopes_columns)
</pre>
<p>I&#8217;m not going to explain all of this, but it&#8217;s pretty cool that all of the ActiveRecord methods take ARel as parameters. Notice that the where clause is missing from this. That&#8217;s because I moved it out into its own scope that I can chain on when I want. This also now uses my default scope which just specifies the order.</p>
<p>I think that this is great because it works with all my scopes and it&#8217;s chainable and everything. I hope that this can be of some use to someone other than me. I learned a lot while trying to do this and I&#8217;m actually pretty surprised that it is all possible. I was half expecting to just have to use my string SQL query and leave it at that.</p>
<img src="http://feeds.feedburner.com/~r/donwriteblog/~4/npoRx-pCIY0" height="1" width="1"/>]]></content:encoded>
			<wfw:commentRss>http://blog.donwilson.net/2011/11/constructing-a-less-than-simple-query-with-rails-and-arel/feed/</wfw:commentRss>
		<slash:comments>2</slash:comments>
		<feedburner:origLink>http://blog.donwilson.net/2011/11/constructing-a-less-than-simple-query-with-rails-and-arel/</feedburner:origLink></item>
		<item>
		<title>I Went To MountainWest RubyConf 2011!</title>
		<link>http://feedproxy.google.com/~r/donwriteblog/~3/QmYfQ9o14Bg/</link>
		<comments>http://blog.donwilson.net/2011/03/i-went-to-mountainwest-rubyconf-2011/#comments</comments>
		<pubDate>Wed, 23 Mar 2011 00:00:09 +0000</pubDate>
		<dc:creator>dontangg</dc:creator>
				<category><![CDATA[Programming]]></category>
		<category><![CDATA[Conference]]></category>

		<guid isPermaLink="false">http://blog.donwilson.net/?p=230</guid>
		<description><![CDATA[I recently went to MountainWest RubyConf 2011 (Mar 17-18).  It was in Salt Lake City at the public library.  It was pretty fun.  I met a guy that recognized me from Taylorsville elementary school!  People were mostly from the western (&#8230;)</p><p><a href="http://blog.donwilson.net/2011/03/i-went-to-mountainwest-rubyconf-2011/">Read the rest of this entry &#187;</a></p>]]></description>
				<content:encoded><![CDATA[<p><a href="http://blog.donwilson.net/wp-content/uploads/2011/03/logo-280.png"><img class="alignright size-full wp-image-231" title="MWRC Logo" src="http://blog.donwilson.net/wp-content/uploads/2011/03/logo-280.png" alt="" width="280" height="177" /></a>I recently went to MountainWest RubyConf 2011 (Mar 17-18).  It was in Salt Lake City at the public library.  It was pretty fun.  I met a guy that recognized me from Taylorsville elementary school!  People were mostly from the western US, but there were people there from the east as well.</p>
<p><span id="more-230"></span>Probably the biggest surprise for me was that I expected for all of the sessions to be centered around Ruby and for everyone to discourage all other languages, but they weren&#8217;t and they didn&#8217;t.  Here is a short list of things that I noticed:</p>
<ul>
<li>Ruby coders are not Ruby exclusive.</li>
<li>Coding is actually called hacking.</li>
<li>Ruby really is a community (so many things about what everyone considers &#8220;core&#8221; to Ruby were contributed by other people).</li>
<li>Bioinformaticians exist.  I met one and he enjoys his job in Arizona!</li>
<li>There are lots of Ruby on Rails jobs in Utah.</li>
<li>Ruby development is largely Mac-centric with some linux.  Windows users are made fun of (light-heartedly).</li>
<li>Everyone is nice and willing to help you and eager to learn (MINASWAN).</li>
<li>IRC is a great way to ask/collaborate with other developers.</li>
<li>There is a big community of Ruby developers in Utah at <a title="Utah Ruby Users Group" href="https://groups.google.com/forum/?pli=1#!forum/urug">URUG</a> that meet together monthly.</li>
<li>Twitter is used way more than I thought.</li>
</ul>
<p>I tried to keep that first list to things that were less techy.  Here is a list of more technical cool things that I learned:</p>
<ul>
<li>There are lots of well-developed Ruby interpreters (MRI, JRuby, Rubinius, MacRuby, Maglev).</li>
<li>If you&#8217;re unhappy with your tools, you should write your own.</li>
<li><a title="Citrus" href="http://mjijackson.com/citrus/index.html">Citrus</a> is a great way to parse.</li>
<li>I want to participate more in the community (ie. <a title="Rails Mentors" href="http://www.railsmentors.org/">Rails Mentors</a> or <a title="Ruby Summer of Code" href="http://rubysoc.org/">Ruby Summer of Code</a> among other things if they do it again).</li>
<li>I want to <a title="Try Redis" href="http://try.redis-db.com/">try Redis</a> and <a title="Try MongoDB" href="http://try.mongodb.org/">MongoDB</a>.</li>
<li>You can create a website using <a href="http://pages.github.com/">GitHub pages</a> for free.</li>
<li>There is a cool Ruby University that is free called <a title="Ruby Mendicant University" href="http://university.rubymendicant.com/">Ruby Mendicant University</a>.</li>
<li><a title="The Pragmatic Bookshelf | Seven Languages in Seven Weeks" href="http://www.pragprog.com/titles/btlang/seven-languages-in-seven-weeks">Learn 7 languages in 7 weeks</a>.</li>
<li>There are better ways to handle concurrency than just using threads (<a title="Concurrency with Actors, Goroutines &amp; Ruby" href="http://www.igvita.com/2010/12/02/concurrency-with-actors-goroutines-ruby/">read more</a>).</li>
</ul>
<p>I also learned some quirky things about the guys in general.  They like:</p>
<ul>
<li><a title="Minecraft" href="http://www.minecraft.net/">Minecraft</a></li>
<li>sparkly unicorns</li>
<li>beer</li>
<li>random animal sounds</li>
<li>sombreros</li>
</ul>
<p>Overall, it was a really interesting, fun experience.  I&#8217;m glad I went.  I learned lots of interesting things and it changed my outlook on different languages and programming in general!</p>
<img src="http://feeds.feedburner.com/~r/donwriteblog/~4/QmYfQ9o14Bg" height="1" width="1"/>]]></content:encoded>
			<wfw:commentRss>http://blog.donwilson.net/2011/03/i-went-to-mountainwest-rubyconf-2011/feed/</wfw:commentRss>
		<slash:comments>1</slash:comments>
		<feedburner:origLink>http://blog.donwilson.net/2011/03/i-went-to-mountainwest-rubyconf-2011/</feedburner:origLink></item>
		<item>
		<title>I Contributed to An Open Source Project!</title>
		<link>http://feedproxy.google.com/~r/donwriteblog/~3/eI609TL9Bs0/</link>
		<comments>http://blog.donwilson.net/2010/11/i-contributed-to-an-open-source-project/#comments</comments>
		<pubDate>Mon, 15 Nov 2010 11:00:44 +0000</pubDate>
		<dc:creator>dontangg</dc:creator>
				<category><![CDATA[Programming]]></category>
		<category><![CDATA[open-source]]></category>

		<guid isPermaLink="false">http://don.thewilsonpad.com/?p=98</guid>
		<description><![CDATA[In my last post, I talked about my envelopes budgeting project a little bit. Well, obviously, I need to display numbers as a currency. I found a convenient function in Rails where I could supply a number and it would (&#8230;)</p><p><a href="http://blog.donwilson.net/2010/11/i-contributed-to-an-open-source-project/">Read the rest of this entry &#187;</a></p>]]></description>
				<content:encoded><![CDATA[<p><a href="http://blog.donwilson.net/wp-content/uploads/2010/11/rails.png"><img class="size-medium wp-image-187 alignright" title="Ruby on Rails" src="http://blog.donwilson.net/wp-content/uploads/2010/11/rails-235x300.png" alt="" width="235" height="300" /></a>In my last post, I talked about my envelopes budgeting project a little bit. Well, obviously, I need to display numbers as a currency. I found a convenient function in Rails where I could supply a number and it would format it nicely (eg. $50.12). However, I quickly noticed that negative numbers were formatted incorrectly (eg. $-50.12 instead of <span style="white-space: nowrap;">-$50.12</span>). I did some searching on the internet and found others frustrated with that as well, so I just wrote my own function.</p>
<p>I left it for a while, but then I decided to see if I could contribute my solution to the Ruby on Rails source code. It was a fun process. I had to learn how to use Git a little more. I had to learn more about the way Rails works. But, I was finally able to submit a patch that was accepted and will be incorporated in version 3.0.2 of Rails.</p>
<p><strong>Edit:</strong> It is now incorporated into Rails. You can see my change in the documentation <a href="http://api.rubyonrails.org/classes/ActionView/Helpers/NumberHelper.html">here</a>.<br />
<span id="more-98"></span></p>
<h1>An Overview of What I Did</h1>
<p>Here are the basic steps that I took:</p>
<ol>
<li>Searched for existing tickets and conversations about the issue.</li>
<li>Researched and learned the way that the function was currently working.</li>
<li>Planned out a solution based on research of how it should work.</li>
<li>Cloned the Rails repository and made my changes.</li>
<li>Created a patch and attached it to a ticket to be reviewed by the Rails team.</li>
<li>Implemented feedback from the Rails ticket and submitted patches until it was accepted.</li>
</ol>
<p>That is a lot of steps, but the actual process didn&#8217;t take very long. I started researching it and thinking about it on Friday, October 29 and it was accepted into Rails on Tuesday, November 2. So, that&#8217;s only 5 days and I wasn&#8217;t doing it all the time.</p>
<h1>A Little More Detail</h1>
<p>I thought I would describe in more detail what I did, so that you can do it too, if you want. First of all, I found out that different open source projects want you to contribute in different ways. Obviously, I&#8217;m going to describe the Rails way. They have an article (<a title="Contributing to Rails" href="http://guides.rubyonrails.org/contributing_to_rails.html">http://guides.rubyonrails.org/contributing_to_rails.html</a>) on how to contribute to Rails that I looked at quite a bit.</p>
<h2>Research Current Conditions</h2>
<p>I did a lot of Google searches to see if others were seeing the same problem as me and if there was anyone that had already attempted to fix it. I did find a lot of people with their own little hacks to get it to work the way they wanted. I also found one person several years ago that submitted a patch to fix it, but it went stale and never got incorporated. It was a good way to learn what people wanted and to see suggestions on how it should work.</p>
<h2>Learn And Research Rails</h2>
<p>All of the Rails code is open source (duh, that&#8217;s why I can contribute). It&#8217;s all hosted on <a title="Rails on GitHub" href="https://github.com/rails/rails">GitHub</a>. So, I went to the code and started getting familiar with how the number_to_currency function worked. I found the file I needed to change fairly easily by looking at the <a title="Documentation for number_to_currency" href="http://api.rubyonrails.org/classes/ActionView/Helpers/NumberHelper.html#method-i-number_to_currency">documentation for the function</a>. The path to the file was right there when I clicked view source. Finding the files where the tests were stored was a little more challenging, but not too hard.</p>
<h2>Researched Best Solution</h2>
<p>I knew that this was not a simple issue to resolve. Well, it was a simple issue to resolve, but not a simple issue to decide what the best resolution would be especially because of how much it can vary by locale. So, I looked at other languages to see what they did to determine how to format negative currencies. I looked at all of the people that I found had issues with it and how they wished it would work and I decided what I thought would be the best way to do it.</p>
<h2>Fix It</h2>
<p>Finally, it was time to get my hands dirty. I already had Git installed on my computer and I already had a GitHub account (it&#8217;s free). I went to the Rails repository on Git and I clicked &#8220;Fork.&#8221; This basically creates a copy of the repository under your name. I don&#8217;t know if I would do it this way again, though. In other open source projects, you fork and then when you&#8217;re done, you send a pull request. That&#8217;s not how Rails does it. With Rails, you just make your changes and submit a patch. So, it&#8217;s not necessary to create your own copy under your account.</p>
<p>Once, I had my forked copy, I cloned it onto my computer.</p>
<pre class="brush: bash; light: true; title: ; notranslate">
$ git clone git://github.com/dontangg/rails.git
</pre>
<p>As I&#8217;m sure you know, this basically puts a copy of the repository on my computer in a folder named rails. It also creates a link (called a remote in Git) to the origin on GitHub.</p>
<p>Since we need to make sure that what we have is always in sync with the actual rails repository, we have to add another remote.</p>
<pre class="brush: bash; light: true; title: ; notranslate">
$ git remote add upstream https://github.com/rails/rails.git
</pre>
<p>This creates another remote called upstream (call it what you want) to the main rails repository. Now, we can pull the source from the main repository to make sure we have the latest stuff (if we don&#8217;t I&#8217;d be surprised).</p>
<pre class="brush: bash; light: true; title: ; notranslate">
$ git pull upstream master
</pre>
<p>This pulls the code from upstream into our master branch in our local repository. Now, we can create a branch for our fix. We&#8217;ll call the branch currency-fix.</p>
<pre class="brush: bash; light: true; title: ; notranslate">
$ git checkout -b currency-fix
</pre>
<p>Now, I was ready to make my changes. Once the changes were made, I modified Rails tests to help prevent regression (breaking functionality later on). To run the tests, first I had to make sure that I had all the gems I needed. This is easy now with bundler. Make sure you have bundler.</p>
<pre class="brush: bash; light: true; title: ; notranslate">
$ gem install bundler
</pre>
<p>Then, to install all the needed gems:</p>
<pre class="brush: bash; light: true; title: ; notranslate">
$ bundle install --without db
</pre>
<p>Now, with all the prerequisites installed, I went to the actionpack/test/ directory in rails and ran this command:</p>
<pre class="brush: bash; light: true; title: ; notranslate">
$ ruby -I . template/number_helper_test.rb
Loaded suite template/number_helper_test
Started
....................
Finished in 0.459888 seconds.

20 tests, 212 assertions, 0 failures, 0 errors, 0 skips
</pre>
<p>Sweet, all the tests passed including the ones I added. We just need to make sure that we still have the latest rails stuff and then we&#8217;re ready to go! Let&#8217;s switch back to the master branch and get the code again. Then we&#8217;ll have to switch back to our branch and &#8220;rebase&#8221; our branch on the master.</p>
<pre class="brush: bash; light: true; title: ; notranslate">
$ git checkout master
Switched to branch 'master'
$ git pull upstream master
...
$ git checkout currency-fix
Switched to branch 'currency-fix'
$ git rebase master
</pre>
<p>Rebase basically rewinds our changes back to where we branched from master originally. Then, it applies changes made to the master branch and then it applies our changes again. This way our branch has the latest stuff from the master branch (that it got from the Rails repository).</p>
<h2>Create A Patch And Create A Ticket</h2>
<p>Creating a patch is pretty simple. Just run this:</p>
<pre class="brush: bash; light: true; title: ; notranslate">
$ git format-patch master --stdout &gt; my_new_patch.diff
</pre>
<p>That creates a patch in the directory that you run the command. The Rails community like you to create a ticket in Lighthouse and describe the issue and attach your patch. You can see the ticket I created <a title="My Lighthouse Ticket" href="https://rails.lighthouseapp.com/projects/8994/tickets/5894-number_to_currency-doesnt-format-negative-numbers-correctly">here</a>.</p>
<h2>Implement Feedback and Submit More Patches</h2>
<p>I got some feedback and I had to make a couple more changes and resubmit patches a few times, but the process was always the same. I thought it was a lot of fun and kind of rewarding to see my changes actually get implemented into Rails. My name is now also on a list of 1,693 people that have contributed to Rails. That&#8217;s a lot of people, but I&#8217;m one of them. It was a fun little project for me. I enjoyed it a lot.</p>
<p><a href="http://blog.donwilson.net/wp-content/uploads/2010/11/Screen-shot-2010-11-03-at-11.41.38-PM.png"><img class="aligncenter size-full wp-image-159" title="I'm a Rails contributor!" src="http://blog.donwilson.net/wp-content/uploads/2010/11/Screen-shot-2010-11-03-at-11.41.38-PM.png" alt="" width="824" height="582" /></a></p>
<img src="http://feeds.feedburner.com/~r/donwriteblog/~4/eI609TL9Bs0" height="1" width="1"/>]]></content:encoded>
			<wfw:commentRss>http://blog.donwilson.net/2010/11/i-contributed-to-an-open-source-project/feed/</wfw:commentRss>
		<slash:comments>1</slash:comments>
		<feedburner:origLink>http://blog.donwilson.net/2010/11/i-contributed-to-an-open-source-project/</feedburner:origLink></item>
		<item>
		<title>Envelopes Budgeting Is Out of Sight</title>
		<link>http://feedproxy.google.com/~r/donwriteblog/~3/viYQBBgfwH0/</link>
		<comments>http://blog.donwilson.net/2010/11/envelopes-budgeting-is-out-of-sight/#comments</comments>
		<pubDate>Wed, 10 Nov 2010 11:00:09 +0000</pubDate>
		<dc:creator>dontangg</dc:creator>
				<category><![CDATA[Projects]]></category>
		<category><![CDATA[envelopes]]></category>

		<guid isPermaLink="false">http://don.thewilsonpad.com/?p=149</guid>
		<description><![CDATA[For those of you who think &#8220;out of sight&#8221; means you can&#8217;t see it, think again. &#8220;Out of sight&#8221; means keen, unreal, hunky dory, exquisite, first-class, or awesome. Managing your money is obviously a very important thing to do. Everyone (&#8230;)</p><p><a href="http://blog.donwilson.net/2010/11/envelopes-budgeting-is-out-of-sight/">Read the rest of this entry &#187;</a></p>]]></description>
				<content:encoded><![CDATA[<p><a href="http://blog.donwilson.net/wp-content/uploads/2010/11/envelopes.jpg"><img class="alignright size-medium wp-image-184" title="Envelopes" src="http://blog.donwilson.net/wp-content/uploads/2010/11/envelopes-300x235.jpg" alt="" width="300" height="235" /></a>For those of you who think &#8220;out of sight&#8221; means you can&#8217;t see it, think again. &#8220;Out of sight&#8221; means keen, unreal, hunky dory, exquisite, first-class, or awesome.</p>
<p>Managing your money is obviously a very important thing to do. Everyone comes up with a different way of doing it. I have asked lots of people how they do it and I don&#8217;t think that any one method is the best for everyone. Some people do it in Excel. Some use Quicken or Mint.com. Some have so much money, they don&#8217;t need to think about it. Others have even more money and they pay people to think about their money.</p>
<p>Behind all of these different ways to manage your money, there are two main philosophies behind them. You either create a budget at the beginning of the month and try to spend less than the money you&#8217;ve budgeted in each category. Or, you &#8220;cash&#8221; your paycheck and allocate your cash into different &#8220;envelopes&#8221; and when you go somewhere you only spend out of that cash that you allocated for that expenditure.<br />
<span id="more-149"></span></p>
<h1>Why Use Envelopes?</h1>
<p>Here again, everyone has a different preference. I prefer using envelopes. Here&#8217;s why I like it:</p>
<ul>
<li><strong>You can always be confident that you&#8217;re not using money that you don&#8217;t have.</strong> When you use a traditional budget, you may budget $400 for the month for groceries. That doesn&#8217;t mean that you can go spend all $400 at the beginning of the month. You probably don&#8217;t have all the money you budget for the month at the beginning of the month. When you use envelopes, you are limited to the money you have in the envelope and you know how much you can spend.</li>
<li><strong>It makes it easier to make the once-in-a-while expenditures.</strong> Every year, we have to renew the registration on the car. Who knows how much it will be, but I know it happens every year. Without envelopes, I can budget to set aside a little money every month, but there is no simple way to set that money aside and know how much you&#8217;ve set aside. With envelopes, I put money in that envelope every month and I can completely forget about it until time comes to pay it. It&#8217;s nice not to panic or worry about having money for Christmas, or oil changes.</li>
<li><strong>Your bank account balance grows (which makes you happier and safer).</strong> We&#8217;ve been doing this for a while now and every month, we have all the money that we&#8217;ll spend at the beginning of the month. For example, November just started and all the money that we need for November is already in our bank account. If something bad happened, we have savings, but on top of that we could already last at least a month.</li>
<li><strong>Financial communication is easier. </strong>If you are married and share funds with your spouse, you have to communicate what you&#8217;re spending to the other person. With envelopes, you still have to communicate, but you both know by just looking in the envelope how much you have left for that category of purchases.</li>
</ul>
<p>The downside to this is obviously that you have to go to the bank to get cash every time you get paid and that you have to find a really safe place for your money in your house.</p>
<p>To solve this, there are some computer websites and programs that simulate the act of putting money into envelopes. All of your money stays in your bank and the website just manages what envelopes it is all split into. When you go to buy something, you just have to check how much is in the envelope and force yourself not to spend more.</p>
<h1>The Ideal Setup</h1>
<p>I have personally used <a title="mvelopes" href="http://www.mvelopes.com/">mvelopes.com</a> for a while now. I had a friend that got me to sign up during a promotion where I paid $60 for a year (a year usually costs $130). I like that it is online and I can access it anywhere and that it is an envelopes budgeting system. However, there is plenty that I don&#8217;t like. I don&#8217;t like the cost. I don&#8217;t like that it is all done in Flash. There are lots of features that I don&#8217;t use that confuse me every once in a while (how to handle credit card payments, for one). And there are more negative sides to it that I won&#8217;t talk about because I&#8217;m not really intending to review mvelopes.com. My point is that I don&#8217;t like what I&#8217;m using.</p>
<p>I have found other solutions (like <a title="You Need A Budget" href="http://www.youneedabudget.com/">You Need A Budget</a>), but I haven&#8217;t found one that I want to stick with. My ideal setup would be like this:</p>
<ul>
<li><strong>Online</strong> so that I can access it from my phone, work, or home without requiring any synchronization.</li>
<li><strong>Not in Flash or Java.</strong> Those technologies are great, but something like this can be done with HTML, CSS, and JavaScript and when something online can be done without Flash or Java, it should be.</li>
<li><strong>Very simple.</strong> I want my wife to feel completely comfortable and safe logging in to check balances of our envelopes. Mvelopes.com is too complicated. I know, I know&#8230; it&#8217;s not that complicated, but it needs to be more simple and it can be.</li>
<li><strong>Free.</strong> Obviously.</li>
<li><strong>Budget using envelopes.</strong> <a title="Mint.com" href="http://www.mint.com/">Mint.com</a> is awesome except in this one category. I really like Mint.com, but I like to budget using envelopes even more.</li>
<li><strong>Generate monthly reports.</strong> Since we&#8217;re not actually using envelopes and spending with cash, it&#8217;s easy to make a mistake and overspend in an envelope. It&#8217;s nice to evaluate how we did at the end of every month.</li>
</ul>
<p>Since I have not found anything that suits all those categories and envelopes budgeting websites are hard to come by, I have decided to write my own. Guess what language I&#8217;m using to write it in? If you know me, you probably already knew I was doing this. If you don&#8217;t know me, you can probably guess since my last few posts have revolved around it. Ruby on Rails!!! and I&#8217;m having a blast doing it. Our year of mvelopes.com will expire within the next couple of months, so I&#8217;m really hoping to have it done soon. I&#8217;ll let you know when I&#8217;m done and I&#8217;ll post some screenshots or something.</p>
<img src="http://feeds.feedburner.com/~r/donwriteblog/~4/viYQBBgfwH0" height="1" width="1"/>]]></content:encoded>
			<wfw:commentRss>http://blog.donwilson.net/2010/11/envelopes-budgeting-is-out-of-sight/feed/</wfw:commentRss>
		<slash:comments>3</slash:comments>
		<feedburner:origLink>http://blog.donwilson.net/2010/11/envelopes-budgeting-is-out-of-sight/</feedburner:origLink></item>
		<item>
		<title>Tutorial: Debugging in Ruby</title>
		<link>http://feedproxy.google.com/~r/donwriteblog/~3/3a7p9oImXyY/</link>
		<comments>http://blog.donwilson.net/2010/11/tutorial-debugging-in-ruby/#comments</comments>
		<pubDate>Sat, 06 Nov 2010 02:15:20 +0000</pubDate>
		<dc:creator>dontangg</dc:creator>
				<category><![CDATA[Programming]]></category>
		<category><![CDATA[Ruby]]></category>

		<guid isPermaLink="false">http://don.thewilsonpad.com/?p=114</guid>
		<description><![CDATA[Debugging is extremely useful to find problems in code. I&#8217;m going to give a really brief tutorial on how to use Ruby&#8217;s built-in debugger for the most common debugging reasons. When I debug, these constitute 95% of what I ever (&#8230;)</p><p><a href="http://blog.donwilson.net/2010/11/tutorial-debugging-in-ruby/">Read the rest of this entry &#187;</a></p>]]></description>
				<content:encoded><![CDATA[<p>Debugging is extremely useful to find problems in code. I&#8217;m going to give a really brief tutorial on how to use Ruby&#8217;s built-in debugger for the most common debugging reasons. When I debug, these constitute 95% of what I ever want to do when I&#8217;m debugging. In simple terms, here&#8217;s what I like to do when debugging:</p>
<ul>
<li>Pause the code in the middle of execution (breakpoint)</li>
<li>View the contents of variables (locals, watch, etc.)</li>
<li>Run one line of code at a time (step over, step into, etc.)</li>
<li>Run my own code while the program is paused</li>
</ul>
<p><span id="more-114"></span>Just to be clear, this is not a tutorial on how to use the gem ruby-debug. This is also not a tutorial on how to use irb. There are a lot of great tools and methods out there for debugging, but this is just about how to use the built-in ruby debugger. I am also only going to talk about the basics of debugging in Ruby. The built-in debugger, does much more than what I will show you. Learn more here: <a href="http://www.ruby-doc.org/docs/ProgrammingRuby/html/trouble.html">http://www.ruby-doc.org/docs/ProgrammingRuby/html/trouble.html</a>.</p>
<p>Here is the code I&#8217;m going to be working with:</p>
<pre class="brush: ruby; title: ; notranslate">
# lottery_numbers.rb
def next_lottery_number(last_number)
  case last_number
  when nil
    4
  when 4
    8
  when 8
    15
  when 15
    16
  when 16
    23
  when 23
    42
  else
    nil
  end
end

current_number = 1
while current_number
  current_number = next_lottery_number(current_number)
  puts current_number
end
</pre>
<p>Basically, all that it should do is output the lottery ticket numbers that would make you win the lottery (4, 8, 15, 16, 23, 42). When I run the program nothing outputs. It doesn&#8217;t work and I can&#8217;t figure out why. So, we&#8217;ll debug it.</p>
<p>To start the debugger, we just type:</p>
<pre class="brush: bash; light: true; title: ; notranslate">
ruby -r debug lottery_numbers.rb
</pre>
<p>The -r option tells Ruby to require a library before it runs my program and I specified to require the debug library.</p>
<p>When I run that, it responds with this:</p>
<pre class="brush: bash; light: true; title: ; notranslate">
Debug.rb
Emacs support available.

lottery_numbers.rb:2:def next_lottery_number(last_number)
(rdb:1)
</pre>
<p>It shows the line that it is about to execute. Of course, it skipped the first line because it was a comment and we are now looking at line 2. Just to feel safe that we are where we think we are, lets run &#8216;list&#8217; to see for sure.  (Also, the commands I type all start with (rdb:#).  Everything else is output by the debugger.)</p>
<pre class="brush: bash; light: true; title: ; notranslate">
(rdb:1) list
[-3, 6] in lottery_numbers.rb
   1  # 4 8 15 16 23 42
=&gt; 2  def next_lottery_number(last_number)
   3    case last_number
   4    when nil
   5      4
   6    when 4
</pre>
<p>Yep, that&#8217;s where we are! Ok we&#8217;re not too interested in this line. This line is just going to define a method, let&#8217;s go to the &#8220;next&#8221; line.</p>
<pre class="brush: bash; light: true; title: ; notranslate">
(rdb:1) next
lottery_numbers.rb:21:current_number = 1
</pre>
<p>It skipped the entire method definition because it doesn&#8217;t execute anything inside the method until the method is called. So, now we are on the line that defines our variable. We are definitely interested in this. Let&#8217;s tell it to keep us updated on the contents of that variable by running the &#8220;display&#8221; command.</p>
<pre class="brush: bash; light: true; title: ; notranslate">
(rdb:1) display current_number
1: current_number =
</pre>
<p>Currently, our variable doesn&#8217;t have anything. That will change when we go to the next line (&#8220;n&#8221; is a shortcut for the next command).</p>
<pre class="brush: bash; light: true; title: ; notranslate">
(rdb:1) n
lottery_numbers.rb:22:while current_number
1: current_number = 1
</pre>
<p>Alright, now we can see that our current_number has the value of 1 in it. Everything is going the way we planned it. I&#8217;ll keep going to the next line until I see something suspicious.</p>
<pre class="brush: bash; light: true; title: ; notranslate">
(rdb:1) n
lottery_numbers.rb:23:  current_number = next_lottery_number(current_number)
1: current_number = 1
(rdb:1) n
lottery_numbers.rb:24:  puts current_number
1: current_number =
</pre>
<p>Uh oh! For some reason, current_number was set back to nothing before anything was output. We also learned that the next (n) command steps over methods. It didn&#8217;t take us into the next_lottery_number method. Let&#8217;s quit the debugger, and debug again. This time we&#8217;ll step into the method.</p>
<pre class="brush: bash; light: true; title: ; notranslate">
(rdb:1) q
Really quit? (y/n) y
$ ruby -r debug lottery_numbers.rb
Debug.rb
Emacs support available.

lottery_numbers.rb:2:def next_lottery_number(last_number)
(rdb:1) b 23
Set breakpoint 1 at lottery_numbers.rb:23
(rdb:1) c
Breakpoint 1, toplevel at lottery_numbers.rb:23
lottery_numbers.rb:23:  current_number = next_lottery_number(current_number)
</pre>
<p>Notice that this time, I set a breakpoint on line 23 (b 23) then I told the program to continue (c) until it hit that breakpoint. Now, we&#8217;re ready to step in with the step command (&#8220;s&#8221; is the shortcut).</p>
<pre class="brush: bash; light: true; title: ; notranslate">
(rdb:1) s
lottery_numbers.rb:3:  case last_number
(rdb:1) l
[-2, 7] in lottery_numbers.rb
   1  # 4 8 15 16 23 42
   2  def next_lottery_number(last_number)
=&gt; 3    case last_number
   4    when nil
   5      4
   6    when 4
   7      8
</pre>
<p>Alright! We&#8217;re in the method now. Now we can follow it to see what went wrong.</p>
<pre class="brush: bash; light: true; title: ; notranslate">
(rdb:1) disp last_number
1: last_number = 1
(rdb:1) s
lottery_numbers.rb:24:  puts current_number
1: last_number =
</pre>
<p>Oh, I guess the way that I wrote it, we don&#8217;t really get to see much by stepping into the method. Let&#8217;s experiment. I&#8217;m going to quit the debugger, go back to line 23 and manually set current_number to 4 before it calls the method to get the next number.</p>
<pre class="brush: bash; light: true; title: ; notranslate">
(rdb:1) q
Really quit? (y/n) y
dons-macbook:Sites don$ ruby -r debug lottery_numbers.rb
Debug.rb
Emacs support available.

lottery_numbers.rb:2:def next_lottery_number(last_number)
(rdb:1) b 23
Set breakpoint 1 at lottery_numbers.rb:23
(rdb:1) c
Breakpoint 1, toplevel at lottery_numbers.rb:23
lottery_numbers.rb:23:  current_number = next_lottery_number(current_number)
(rdb:1) current_number = 4
4
(rdb:1) disp current_number
1: current_number = 4
(rdb:1) l
[18, 27] in lottery_numbers.rb
   18    end
   19  end
   20
   21  current_number = 1
   22  while current_number
=&gt; 23    current_number = next_lottery_number(current_number)
   24    puts current_number
   25  end
(rdb:1) n
lottery_numbers.rb:24:  puts current_number
1: current_number = 8
</pre>
<p>To run my own line of code, all I had to do is type in the code that I wanted to run! That&#8217;s pretty easy, right? And look! When I started out as 4, it correctly set the next number to 8. Well, as you probably noticed, I originally thought that I would pass nil into the function the first time through. That changed when I got to the bottom and I realized that I couldn&#8217;t pass nil in if I wanted to use it in the while loop the way that I did. Then, I just forgot that it would affect the method that I wrote. Let&#8217;s make a small change to line 4 to check for the number 1 instead of nil.</p>
<pre class="brush: ruby; highlight: [3]; title: ; notranslate">
def next_lottery_number(last_number)
  case last_number
  when 1
    4
</pre>
<pre class="brush: bash; light: true; title: ; notranslate">
$ ruby lottery_numbers.rb
4
8
15
16
23
42
</pre>
<p>Awesome! When we run the program now, it works!</p>
<p>This was a pretty basic example and it doesn&#8217;t show all the commands you can use with the built-in debugger. I hope it can be a quick helpful tutorial for people trying to debug their Ruby code.</p>
<p>This would actually be a fun way to debug: <a href="http://www.youtube.com/watch?v=8_HSCMTo6xw">YouTube clip</a>.</p>
<img src="http://feeds.feedburner.com/~r/donwriteblog/~4/3a7p9oImXyY" height="1" width="1"/>]]></content:encoded>
			<wfw:commentRss>http://blog.donwilson.net/2010/11/tutorial-debugging-in-ruby/feed/</wfw:commentRss>
		<slash:comments>0</slash:comments>
		<feedburner:origLink>http://blog.donwilson.net/2010/11/tutorial-debugging-in-ruby/</feedburner:origLink></item>
		<item>
		<title>Programming Is Art</title>
		<link>http://feedproxy.google.com/~r/donwriteblog/~3/5oINnYus5oU/</link>
		<comments>http://blog.donwilson.net/2010/11/programming-is-art/#comments</comments>
		<pubDate>Wed, 03 Nov 2010 03:27:49 +0000</pubDate>
		<dc:creator>dontangg</dc:creator>
				<category><![CDATA[Opinion]]></category>
		<category><![CDATA[Programming]]></category>

		<guid isPermaLink="false">http://don.thewilsonpad.com/?p=99</guid>
		<description><![CDATA[&#8220;When you don&#8217;t create things, you become defined by your tastes rather than ability. your tastes only narrow &#38; exclude people. so create.&#8221; _why the lucky stiff I like this quote. One of the reasons the I like programming on (&#8230;)</p><p><a href="http://blog.donwilson.net/2010/11/programming-is-art/">Read the rest of this entry &#187;</a></p>]]></description>
				<content:encoded><![CDATA[<blockquote>
<div id="attachment_133" class="wp-caption alignright" style="width: 160px"><a href="http://blog.donwilson.net/wp-content/uploads/2010/11/binary-art.png"><img class="alignright size-thumbnail wp-image-133" title="Binary Art" src="http://blog.donwilson.net/wp-content/uploads/2010/11/binary-art-150x150.png" alt="" width="150" height="150" /></a><p class="wp-caption-text">Binary Art</p></div>
<p>&#8220;When you don&#8217;t create things, you become defined by your tastes rather than ability. your tastes only narrow &amp; exclude people. so create.&#8221;<br />
<cite>_why the lucky stiff</cite></p></blockquote>
<p>I like this quote. One of the reasons the I like programming on the computer is because it is my way of being creative. What do you think of this quote?</p>
<p><span id="more-99"></span>It kind of reminds me of this quote from the movie Dead Poets Society:</p>
<blockquote><p>&#8220;We don&#8217;t read and write poetry because it&#8217;s cute. We read and write poetry because we are members of the human race. And the human race is filled with passion. And medicine, law, business, engineering, these are noble pursuits and necessary to sustain life. But poetry, beauty, romance, love, these are what we stay alive for. To quote from Whitman, &#8220;O me! O life!&#8230; of the questions of these recurring; of the endless trains of the faithless&#8230; of cities filled with the foolish; what good amid these, O me, O life?&#8221; Answer. That you are here &#8211; that life exists, and identity; that the powerful play goes on and you may contribute a verse. That the powerful play<em>goes on</em> and you may contribute a verse. What will your verse be?&#8221;<br />
<cite>John Keating</cite></p></blockquote>
<p>I&#8217;d like to think that there are many ways that I have contributed a verse, but one of them is definitely through the web development and computer programming that I have done. For me, writing code is my way of being an artist and my art project consists of different layers of beauty:</p>
<ul>
<li>How nice and usable is it for the user?</li>
<li>How well does it serve the needs of the user?</li>
<li>How beautiful is the actual code? Is it efficient? Is it well documented? Does it look nice?</li>
</ul>
<p>I can&#8217;t say that I&#8217;ve always had the time or been in the mood to do this well every time, but it important to me.</p>
<p>I&#8217;m going to try to quickly explain the languages that I have experience with what I like or don&#8217;t like about them. This isn&#8217;t going to be an in-depth analysis of them&#8230; just a little bit about them&#8230; the main reasons that I have.</p>
<h1>My Experience With Different Languages</h1>
<p>I started telling the computer what to do when I was 10 years old and I used HyperCard. It used a language called HyperTalk and it was based on a concept that a program consists of a stack of user interfaces. It was a good place to start for me. It is what got me excited about programming. It&#8217;s too bad they don&#8217;t make it anymore.</p>
<p>Then I found a book in my school library (in 6th grade I think) on BASIC with tutorials on how to create games. I learned the basics of subroutines/functions as well as command line input/output. I had a blast with that one, but beyond that book, I didn&#8217;t have much resource for learning more.We didn&#8217;t have the internet (even if we did, I don&#8217;t think that there would be much of a resource back then). Today, I definitely don&#8217;t like VB.Net very much. C# is much better. In VB, you have to put &#8220;Then&#8221; after your If statement among many other syntax vegetables.  Yuck!</p>
<p>Here is a little BASIC. Kind of nostalgic&#8230;</p>
<pre class="brush: vb; title: ; notranslate">
INPUT &quot;What is your name: &quot;, UserName$
PRINT &quot;Hello &quot;; UserName$
DO
  INPUT &quot;How many stars do you want: &quot;, NumStars
  Stars$ = STRING$(NumStars, &quot;*&quot;)
  PRINT Stars$
  DO
    INPUT &quot;Do you want more stars? &quot;, Answer$
  LOOP UNTIL Answer$ &lt;&gt; &quot;&quot;
  Answer$ = LEFT$(Answer$, 1)
LOOP WHILE UCASE$(Answer$) = &quot;Y&quot;
PRINT &quot;Goodbye &quot;; UserName$
</pre>
<p>For my math classes in Junior High and High School I had a TI-85 and I created some games on my calculator. I don&#8217;t know the name of the language used on the calculator. Luckily, the calculator came with a great little book with descriptions on all the commands you could issue to the calculator. This was awesome because I was great at math and finished my assignments quickly which left plenty of time for more work on my calculator during class!</p>
<p>My dad noticed my interest in programming and he wanted to learn too. So, we went to the bookstore and bought a book on C that we read together and did the exercises together. I loved learning C more than any other language to that point.  It was the first language that I appreciated not only for what I could tell the computer to do with it, but also the way that it looked. To this day I like the wide range of ways that you can accomplish things. Programming in C/C++ feels like I&#8217;m breathing a cleaner air and that I have more freedom than any other language.</p>
<p>In High School, I had a computer science class and we learned both C++ and Pascal. I liked Pascal, but I loved C++.</p>
<p>Of course, when I went to college, almost all of the computer science classes were in Java. I really liked Java. Of all the other languages I had learned to that point, it reminded me most of C++. I know that&#8217;s weird, but think it was just because it&#8217;s object oriented. I don&#8217;t understand why, but I have this weird opinion of Java. I really enjoy programming in it, but I don&#8217;t enjoy using programs created with it. Maybe I should figure out why, but I don&#8217;t really care. <img src='http://blog.donwilson.net/wp-includes/images/smilies/icon_smile.gif' alt=':)' class='wp-smiley' />  In college, I also had classes on C++, Python, and Perl. Python and Perl were okay languages to use, but for some reason I found myself avoiding them rather than interested in them.</p>
<p>During college, but my job provided an opportunity to learn how to do web development. At first, I didn&#8217;t like it very much. It didn&#8217;t feel like programming to me. I kept doing it anyways, and I eventually learned to appreciate PHP and I learned to love JavaScript, HTML, and CSS. Today, I feel neutral about PHP, but I really like HTML, CSS, and JavaScript. It is so easy and fun to deliver a great experience to people on the web.</p>
<p>When I graduated, I got a job doing web development with ASP.NET using C#. I really like C# because it reminds me of C++.</p>
<h1>And Then There Was Ruby</h1>
<p>With all the web development that I&#8217;ve done, at some point, I stumbled across Ruby on Rails. It has taken me a little bit of writing, but that is actually the reason I wanted to write this post. I love Ruby and I love Rails! I still love C++, but I feel like Ruby gives me a lot of what I love about the beauty of code that I enjoy about C++. And, when you pair it with Rails, I get HTML, CSS, and JavaScript too.  Everything that I love.</p>
<p>A man named _why said, &#8220;To write Ruby code is to love&#8230; to feel passion.&#8221; I don&#8217;t know if I would use the same words, but I feel similarly. I really feel like I&#8217;m creating a work of art when I write Ruby code. It&#8217;s like I&#8217;m creating an awesome sculpture for the city square or painting the ceiling of a chapel. I know that may sound crazy or stupid. I may be exaggerating a little too, but it definitely is more for me than just getting to the end result.</p>
<p>If you want to try Ruby or learn more about Ruby on Rails, here&#8217;s where I would start:<br />
Try Ruby: <a title="Try Ruby!" href="http://tryruby.org/">http://tryruby.org/</a> (this is a quick, fun, and easy way to try Ruby)<br />
Railscasts: <a title="Railscasts" href="http://railscasts.com/">http://railscasts.com/<br />
</a>Rails for Zombies: <a title="Rails for Zombies" href="http://railsforzombies.org/">http://railsforzombies.org/</a><br />
Rails Guides: <a title="Rails Guides" href="http://guides.rubyonrails.org/">http://guides.rubyonrails.org/</a><br />
Agile Development with Rails: <a title="Agile Development with Rails" href="http://pragprog.com/titles/rails3/agile-web-development-with-rails-third-edition">http://pragprog.com/titles/rails3/agile-web-development-with-rails-third-edition</a></p>
<img src="http://feeds.feedburner.com/~r/donwriteblog/~4/5oINnYus5oU" height="1" width="1"/>]]></content:encoded>
			<wfw:commentRss>http://blog.donwilson.net/2010/11/programming-is-art/feed/</wfw:commentRss>
		<slash:comments>0</slash:comments>
		<feedburner:origLink>http://blog.donwilson.net/2010/11/programming-is-art/</feedburner:origLink></item>
	</channel>
</rss>
