<?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:atom="http://www.w3.org/2005/Atom" xmlns:openSearch="http://a9.com/-/spec/opensearch/1.1/" xmlns:georss="http://www.georss.org/georss" xmlns:feedburner="http://rssnamespace.org/feedburner/ext/1.0" version="2.0"><channel><atom:id>tag:blogger.com,1999:blog-689869310107675036</atom:id><lastBuildDate>Sat, 14 Nov 2009 19:20:35 +0000</lastBuildDate><title>Hackido</title><description /><link>http://www.hackido.com/</link><managingEditor>noreply@blogger.com (vince wadhwani)</managingEditor><generator>Blogger</generator><openSearch:totalResults>49</openSearch:totalResults><openSearch:startIndex>1</openSearch:startIndex><openSearch:itemsPerPage>25</openSearch:itemsPerPage><atom10:link xmlns:atom10="http://www.w3.org/2005/Atom" rel="self" href="http://feeds.feedburner.com/Hackido" type="application/rss+xml" /><atom10:link xmlns:atom10="http://www.w3.org/2005/Atom" rel="hub" href="http://pubsubhubbub.appspot.com" /><item><guid isPermaLink="false">tag:blogger.com,1999:blog-689869310107675036.post-8291080333467459045</guid><pubDate>Sat, 14 Nov 2009 18:49:00 +0000</pubDate><atom:updated>2009-11-14T14:20:35.869-05:00</atom:updated><category domain="http://www.blogger.com/atom/ns#">linux</category><category domain="http://www.blogger.com/atom/ns#">hardware</category><category domain="http://www.blogger.com/atom/ns#">ubuntu</category><title>Trying &amp; Failing with Linux &amp; The HP Envy</title><description>&lt;a onblur="try {parent.deselectBloggerImageGracefully();} catch(e) {}" href="http://2.bp.blogspot.com/_xyjRMd2gFJo/Sv7_Mqyv1iI/AAAAAAAAAFU/jC6rf5FJ7Vo/s1600-h/envy.jpg"&gt;&lt;img style="float:left; margin:0 10px 10px 0;cursor:pointer; cursor:hand;width: 200px; height: 133px;" src="http://2.bp.blogspot.com/_xyjRMd2gFJo/Sv7_Mqyv1iI/AAAAAAAAAFU/jC6rf5FJ7Vo/s200/envy.jpg" border="0" alt=""id="BLOGGER_PHOTO_ID_5404037196001826338" /&gt;&lt;/a&gt;I currently use a Dell XPS m1330 as my full time work laptop. After playing around with Sidux for about a year I settled down on Ubuntu where I've been happily plugging away for quite a while.  The biggest nag I have is that my hardware is starting to show its age.  Since it's been about 2 years I decided to reward myself with the beautiful, powerful, and expensive HP Envy 13.&lt;br /&gt;&lt;br /&gt;Loaded with a great graphics card and 5GB of RAM, I expected that this stunning crafted metal would serve me well for the next 2 years.  But, after about 36 hours with the machine I decided to send it back.  Here's why:&lt;br /&gt;&lt;br /&gt;&lt;span class="fullpost"&gt;&lt;br /&gt;&lt;span style="font-weight:bold;"&gt;1.&lt;/span&gt; &lt;span style="font-style:italic;"&gt;BIOS problems.&lt;/span&gt;  After doing some digging around I discovered that the BIOS (version F.05 of this writing). Didn't play nicely with linux.  Apparently it does not correctly report temperature and whatnot making Speedstep and ACPI problematic or non-functioning.  &lt;a href="http://h30434.www3.hp.com/psg/board/message?board.id=OS&amp;message.id=23381#M23381"&gt;link&lt;/a&gt;&lt;br /&gt;&lt;br /&gt;&lt;span style="font-weight:bold;"&gt;2.&lt;/span&gt;&lt;span style="font-style:italic;"&gt; The trackpad was not functional in linux.&lt;/span&gt;  People complained about the trackpad behavior in Windows but frankly I thought it was passable.. something I'd get used to after a while or even learn to enjoy with a few software tweaks.  Unfortunately, the synaptics drivers in linux didn't allow me to even click on the trackpad. I was relegated to tapping to click.  That's well and good but it means that right-clicking isn't possible without major hacking.  &lt;br /&gt;&lt;br /&gt;I felt that both issues above might eventually get fixed but I couldn't use Windows 7 while I waited.  (BTW, it's still a horrible operating system..)  As a last resort I thought about installing VMWare 7 and using linux full-time within it.  Not ideal, sure, but it would hold me over for a few months while drivers and bios updates rolled out.&lt;br /&gt;&lt;br /&gt;Unfortunately, &lt;span style="font-style:italic;"&gt;VMWare 7 won't work on the Envy 13 out of the box&lt;/span&gt;. I kept getting an error about it being unable to access the .vmdx file.  Googling around I discovered the error is basically caused by either the Firewall, Virus detection (both of which I had disabled) or any of a billion 3rd party preinstalled apps.&lt;br /&gt;&lt;br /&gt;And that's where I decided my time had been sufficiently wasted.  &lt;br /&gt;&lt;br /&gt;So if any readers are considering the Envy 13 in conjunction with Linux, I'd suggest taking a pass for now.  By the time HP decide to take linux seriously and provide basic support then maybe the Envy 13/15 will be more reasonably priced.&lt;br /&gt;&lt;br /&gt;Lastly, if anyone has a suggestion for a laptop under 1" thick (everywhere.. no games please), with a decent graphics card, please post a link below.&lt;br /&gt;&lt;/span&gt;&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/689869310107675036-8291080333467459045?l=www.hackido.com'/&gt;&lt;/div&gt;&lt;img src="http://feeds.feedburner.com/~r/Hackido/~4/QhiL4dLcF8Y" height="1" width="1"/&gt;</description><link>http://feedproxy.google.com/~r/Hackido/~3/QhiL4dLcF8Y/trying-failing-with-linux-hp-envy.html</link><author>noreply@blogger.com (vince wadhwani)</author><media:thumbnail xmlns:media="http://search.yahoo.com/mrss/" url="http://2.bp.blogspot.com/_xyjRMd2gFJo/Sv7_Mqyv1iI/AAAAAAAAAFU/jC6rf5FJ7Vo/s72-c/envy.jpg" height="72" width="72" /><thr:total xmlns:thr="http://purl.org/syndication/thread/1.0">0</thr:total><feedburner:origLink>http://www.hackido.com/2009/11/trying-failing-with-linux-hp-envy.html</feedburner:origLink></item><item><guid isPermaLink="false">tag:blogger.com,1999:blog-689869310107675036.post-2019862065766599625</guid><pubDate>Sat, 07 Nov 2009 16:40:00 +0000</pubDate><atom:updated>2009-11-09T04:35:09.407-05:00</atom:updated><category domain="http://www.blogger.com/atom/ns#">ruby</category><category domain="http://www.blogger.com/atom/ns#">rails</category><category domain="http://www.blogger.com/atom/ns#">karmic</category><category domain="http://www.blogger.com/atom/ns#">ubuntu</category><title>Install Ruby on Rails on Ubuntu Karmic Koala 9.10</title><description>&lt;a onblur="try {parent.deselectBloggerImageGracefully();} catch(e) {}" href="http://2.bp.blogspot.com/_xyjRMd2gFJo/STb6O5fWtwI/AAAAAAAAACI/WfvhPhSAEuE/s1600-h/rails.jpg"&gt;&lt;img style="float:left; margin:0 10px 10px 0;cursor:pointer; cursor:hand;width: 90px; height: 115px;" src="http://2.bp.blogspot.com/_xyjRMd2gFJo/STb6O5fWtwI/AAAAAAAAACI/WfvhPhSAEuE/s320/rails.jpg" border="0" alt=""id="BLOGGER_PHOTO_ID_5275679147368560386" /&gt;&lt;/a&gt;If you're running Ubuntu 9.10 and want to install Ruby on Rails I've put together a quick tutorial for you.  Not tremendously much has changed since the last tutorial for Jaunty Jackalope.  Unicorn is out and while I think it's nifty, I'm going to wait a little while before playing with it.  For now my money is still on Phusion Passenger as being the right tool for the job.  If all that seems fine, let's get to the details.&lt;br /&gt;&lt;br /&gt;&lt;span class="fullpost"&gt;&lt;br /&gt;&lt;script type="text/javascript"&gt;&lt;br /&gt;    if (typeof window.Delicious == "undefined") window.Delicious = {};&lt;br /&gt;    Delicious.BLOGBADGE_DEFAULT_CLASS = 'delicious-blogbadge-line';&lt;br /&gt;&lt;/script&gt;&lt;br /&gt;&lt;script src="http://images.del.icio.us/static/js/blogbadge.js"&gt;&lt;/script&gt;&lt;br /&gt;&lt;b&gt;Step 1&lt;/b&gt;: As usual, the first thing we'll want to do is make sure your version of Ubuntu is up to date.:&lt;br /&gt;&lt;pre&gt;sudo apt-get update&lt;br /&gt;sudo apt-get dist-upgrade&lt;/pre&gt;&lt;br /&gt;&lt;br /&gt;If you see this warning it means we have a little more work to do.&lt;br /&gt;&lt;br /&gt;&lt;pre&gt;perl: warning: Setting locale failed.&lt;br /&gt;perl: warning: Please check that your locale settings:&lt;br /&gt; LANGUAGE = (unset),&lt;br /&gt; LC_ALL = (unset),&lt;br /&gt; LANG = "en_US.UTF-8"&lt;br /&gt;    are supported and installed on your system.&lt;br /&gt;perl: warning: Falling back to the standard locale ("C").&lt;br /&gt;&lt;/pre&gt;&lt;br /&gt;&lt;br /&gt;Let's go ahead and set your locale now. (I'm using en-US in this example.. feel free to substitute for your region)&lt;br /&gt;&lt;br /&gt;&lt;pre&gt;sudo locale-gen en_US.UTF-8&lt;br /&gt;sudo /usr/sbin/update-locale LANG=en_US.UTF-8&lt;br /&gt;&lt;/pre&gt;&lt;br /&gt;&lt;br /&gt;&lt;b&gt;Step 2:&lt;/b&gt; We'll be installing some software that needs to be built so we'll need to get packages required for compiling. With Ubuntu, you can type this single command and get everything you need:&lt;br /&gt;&lt;pre&gt;sudo apt-get install build-essential&lt;/pre&gt;&lt;br /&gt;&lt;br /&gt;&lt;b&gt;Step 3:&lt;/b&gt; Once you've got the tools, it's time to install MySQL and Ruby. If you're using SQLite you may not need all this stuff. Otherwise, just copy and paste this command into your terminal if you're in a hurry. As of Karmic Koala, we're using MySQL 5.1:&lt;br /&gt;&lt;pre&gt;sudo apt-get install ruby ri rdoc mysql-server libmysql-ruby ruby1.8-dev irb1.8 libdbd-mysql-perl libdbi-perl libmysql-ruby1.8 libmysqlclient15off libnet-daemon-perl libplrpc-perl libreadline-ruby1.8 libruby1.8 mysql-client-5.1 mysql-common mysql-server-5.1 rdoc1.8 ri1.8 ruby1.8 irb libopenssl-ruby libopenssl-ruby1.8 libhtml-template-perl mysql-server-core-5.1 libmysqlclient16 libreadline5 psmisc&lt;br /&gt;&lt;/pre&gt;&lt;br /&gt;If you hadn't previously installed MySQL you'll be asked to set a root password.  You don't have to, of course (it will bug you no fewer than 3 times if you opt not to) but I strongly recommend it.  You'll need this password when you populate your rails config/database.yml file so be sure not to forget it.&lt;br /&gt;&lt;br /&gt;&lt;b&gt;Step 4:&lt;/b&gt; Grab the latest ruby gems and install them. As always be sure to check &lt;a href="http://rubyforge.org/projects/rubygems/"&gt;rubyforge.org&lt;/a&gt; to make sure you're grabbing the latest one.  As of this writing it's 1.3.5 but it never hurts to confirm.&lt;br /&gt;&lt;pre&gt;wget http://rubyforge.org/frs/download.php/60718/rubygems-1.3.5.tgz&lt;br /&gt;tar xvzf rubygems-1.3.5.tgz&lt;br /&gt;cd rubygems-1.3.5&lt;br /&gt;sudo ruby setup.rb&lt;br /&gt;&lt;/pre&gt;&lt;br /&gt;Once it's done you can remove the .tgz file and erase the rubygems-1.3.5 directory too.  &lt;br /&gt;&lt;br /&gt;&lt;b&gt;Step 5:&lt;/b&gt; On the command line, type gem -v.  if you get this message we need to make some symlinks:&lt;br /&gt;&lt;br /&gt;&lt;pre&gt;The program 'gem' can be found in the following packages:&lt;br /&gt; * rubygems1.8&lt;br /&gt; * rubygems1.9&lt;br /&gt;Try: sudo apt-get install &lt;selected package&gt;&lt;br /&gt;-bash: gem: command not found&lt;br /&gt;&lt;/pre&gt;&lt;br /&gt;Let's create those symlinks now:&lt;br /&gt;&lt;br /&gt;&lt;pre&gt;sudo ln -s /usr/bin/gem1.8 /usr/local/bin/gem&lt;br /&gt;sudo ln -s /usr/bin/ruby1.8 /usr/local/bin/ruby&lt;br /&gt;sudo ln -s /usr/bin/rdoc1.8 /usr/local/bin/rdoc&lt;br /&gt;sudo ln -s /usr/bin/ri1.8 /usr/local/bin/ri&lt;br /&gt;sudo ln -s /usr/bin/irb1.8 /usr/local/bin/irb&lt;/pre&gt;&lt;br /&gt;&lt;br /&gt;&lt;br /&gt;&lt;b&gt;Step 6:&lt;/b&gt;  Install Ruby on Rails! You can leave off the --no-rdoc and --no-ri switches if you're on a machine with plenty of ram.  But just in case you've got a more modest setup (say 256MB or less) I'd just use the following:&lt;br /&gt;&lt;pre&gt;sudo gem install rails --no-rdoc --no-ri&lt;/pre&gt;&lt;br /&gt;&lt;br /&gt;If you're just doing local development then you are basically done. You may want to install additional gems.  If you want to deploy Ruby on Rails onto a server then it's time to setup Nginx and Phusion.&lt;br /&gt;&lt;br /&gt;&lt;b&gt;Step 7:&lt;/b&gt; As I mentioned earlier, Unicorn may be the new hotness but I'm going to wait a while before I put my customers on that stack.  The folks responsible for &lt;a href="http://www.modrails.com/"&gt;Phusion Passenger&lt;/a&gt;(Hongli Lai &amp; Ninh Bui) are incredibly smart and I think they'll look at Unicorn and make some improvements to Phusion to eek out even more performance.  The short of it is that I'm still a big believer in Phusion so I'm going to install it for production and recommend that you do too:&lt;br /&gt;&lt;br /&gt;&lt;pre&gt;sudo apt-get install libc6 libpcre3 libpcre3-dev libpcrecpp0 libssl0.9.8 libssl-dev zlib1g zlib1g-dev lsb-base&lt;/pre&gt;&lt;br /&gt;&lt;br /&gt;&lt;br /&gt;&lt;b&gt;Step 8:&lt;/b&gt; We're going to create a directory for your application.  In anticipation of Capistrano, let's put it in /var/www/myapp/current.  Swap out the myapp with anything you like.&lt;br /&gt;&lt;pre&gt;sudo mkdir -p /var/www/myapp/current&lt;/pre&gt;&lt;br /&gt;If you've got an existing Rails application, it doesn't hurt to populate that directory now.  Just make sure that the root to the public directory is /var/www/myapp/current/public.  Don't forget to chown it for www-data:&lt;br /&gt;&lt;br /&gt;&lt;pre&gt;sudo chown -R www-data:www-data /var/www/myapp/current/&lt;/pre&gt;&lt;br /&gt;&lt;br /&gt;&lt;br /&gt;&lt;b&gt;Step 9:&lt;/b&gt; Now it's time to install Phusion Passenger and let it do it's magic.  &lt;br /&gt;&lt;br /&gt;&lt;pre&gt;sudo gem install passenger&lt;br /&gt;sudo passenger-install-nginx-module&lt;/pre&gt;&lt;br /&gt;At this point you'll be greeted with two options.  The first will allow Passenger to do all the work while the second, for advanced users, allows you to point Phusion to  your pre-installed Nginx.  We're going to make life easy on ourselves and choose option 1.  I'd also recommend keeping the default path (/opt/nginx).&lt;br /&gt;&lt;br /&gt;The Nginx configuration file (nginx.conf) file is in /opt/nginx/conf/  They've done you the favor of adding the lines you need to get going.  Defining the configuration file is beyond the scope of this tutorial, but I've included a sample file which you can download.  This file assumes your application is in /var/www/myapp/current.&lt;br /&gt;&lt;br /&gt;&lt;a href="http://vince71.googlepages.com/nginx.conf"&gt;Sample nginx.conf file for Ruby on Rails, Nginx, Phusion Passenger.&lt;/a&gt;&lt;br /&gt;&lt;br /&gt;&lt;br /&gt;&lt;b&gt;Step 10:&lt;/b&gt;  Time to make some Nginx tweaks for Ubuntu/Debian.  If you're used to running nginx as installed by Debian or Ubuntu then you might notice that you've lost the familiar way to start and stop nginx.  Gone is &lt;span style="font-style:italic;"&gt;/etc/init.d/nginx stop&lt;/span&gt; and &lt;span style="font-style:italic;"&gt;/etc/init.d/nginx/start&lt;/span&gt;.  To get it back, copy (or &lt;a href="http://vince71.googlepages.com/nginx"&gt;download&lt;/a&gt;) this into a file called nginx in /etc/init.d/ (as root)&lt;br /&gt;&lt;pre&gt;#! /bin/sh&lt;br /&gt;&lt;br /&gt;### BEGIN INIT INFO&lt;br /&gt;# Provides:          nginx&lt;br /&gt;# Required-Start:    $all&lt;br /&gt;# Required-Stop:     $all&lt;br /&gt;# Default-Start:     2 3 4 5&lt;br /&gt;# Default-Stop:      0 1 6&lt;br /&gt;# Short-Description: starts the nginx web server&lt;br /&gt;# Description:       starts nginx using start-stop-daemon&lt;br /&gt;### END INIT INFO&lt;br /&gt;&lt;br /&gt;PATH=/opt/nginx/sbin:/sbin:/bin:/usr/sbin:/usr/bin&lt;br /&gt;DAEMON=/opt/nginx/sbin/nginx&lt;br /&gt;NAME=nginx&lt;br /&gt;DESC=nginx&lt;br /&gt;&lt;br /&gt;test -x $DAEMON || exit 0&lt;br /&gt;&lt;br /&gt;# Include nginx defaults if available&lt;br /&gt;if [ -f /etc/default/nginx ] ; then&lt;br /&gt;        . /etc/default/nginx&lt;br /&gt;fi&lt;br /&gt;&lt;br /&gt;set -e&lt;br /&gt;&lt;br /&gt;case "$1" in&lt;br /&gt;  start)&lt;br /&gt;        echo -n "Starting $DESC: "&lt;br /&gt;        start-stop-daemon --start --quiet --pidfile /opt/nginx/logs/$NAME.pid \&lt;br /&gt;                --exec $DAEMON -- $DAEMON_OPTS&lt;br /&gt;        echo "$NAME."&lt;br /&gt;        ;;&lt;br /&gt;  stop)&lt;br /&gt;        echo -n "Stopping $DESC: "&lt;br /&gt;        start-stop-daemon --stop --quiet --pidfile /opt/nginx/logs/$NAME.pid \&lt;br /&gt;                --exec $DAEMON&lt;br /&gt;        echo "$NAME."&lt;br /&gt;        ;;&lt;br /&gt;  restart|force-reload)&lt;br /&gt;        echo -n "Restarting $DESC: "&lt;br /&gt;        start-stop-daemon --stop --quiet --pidfile \&lt;br /&gt;                /opt/nginx/logs/$NAME.pid --exec $DAEMON&lt;br /&gt;        sleep 1&lt;br /&gt;        start-stop-daemon --start --quiet --pidfile \&lt;br /&gt;                /opt/nginx/logs/$NAME.pid --exec $DAEMON -- $DAEMON_OPTS&lt;br /&gt;        echo "$NAME."&lt;br /&gt;        ;;&lt;br /&gt;  reload)&lt;br /&gt;          echo -n "Reloading $DESC configuration: "&lt;br /&gt;          start-stop-daemon --stop --signal HUP --quiet --pidfile     /opt/nginx/logs/$NAME.pid \&lt;br /&gt;              --exec $DAEMON &lt;br /&gt;          echo "$NAME."&lt;br /&gt;          ;;&lt;br /&gt;      *)&lt;br /&gt;            N=/etc/init.d/$NAME&lt;br /&gt;            echo "Usage: $N {start|stop|restart|reload|force-reload}" &gt;&amp;2&lt;br /&gt;            exit 1   &lt;br /&gt;            ;;&lt;br /&gt;    esac&lt;br /&gt;&lt;br /&gt;    exit 0&lt;br /&gt;&lt;/pre&gt;&lt;br /&gt;&lt;br /&gt;Next, let's set the permissions and make nginx load on a reboot:&lt;br /&gt;&lt;br /&gt;&lt;pre&gt;sudo chmod +x /etc/init.d/nginx&lt;br /&gt;sudo /usr/sbin/update-rc.d -f nginx defaults&lt;/pre&gt;&lt;br /&gt;&lt;br /&gt;Now you should be able to start and stop nginx using the command you're used to:&lt;br /&gt;&lt;br /&gt;&lt;pre&gt;sudo /etc/init.d/nginx start&lt;/pre&gt;&lt;br /&gt;&lt;br /&gt;&lt;br /&gt;&lt;b&gt;Bonus steps&lt;/b&gt; In case it's not already installed, let's grab the perquisites and then install the mysql gem.  This will improve performance on your webserver:&lt;br /&gt;&lt;pre&gt;sudo apt-get install libmysqlclient-dev&lt;br /&gt;sudo gem install mysql --no-rdoc --no-ri&lt;br /&gt;&lt;/pre&gt;&lt;br /&gt;&lt;br /&gt;You should also look into using a helper for deployment. I still use &lt;a href="http://www.capify.org/index.php/Capistrano"&gt;Capistrano&lt;/a&gt; but there are alternatives such as &lt;a href="http://rubyhitsquad.com/Vlad_the_Deployer.html"&gt;Vlad the Deployer&lt;/a&gt;, &lt;a href="http://reductivelabs.com/products/puppet/"&gt;Puppet&lt;/a&gt; and others.  I will also recommend that if you go with Capistrano that you check out the &lt;a href="http://gemcutter.org/gems/capistrano-ext"&gt;capistrano-ext gem&lt;/a&gt; which allows you to do &lt;a href="https://boxpanel.blueboxgrp.com/public/the_vault/index.php/Capistrano_Multi_Stage_Instructions"&gt;multi-stage deployments&lt;/a&gt;.&lt;br /&gt;&lt;br /&gt;&lt;br /&gt;&lt;b&gt;Troubleshooting&lt;/b&gt;  If things didn't go smoothly, here are some things to check:&lt;br /&gt;&lt;br /&gt;1. There's an error log for nginx in /opt/nginx/logs/  Try looking to see if you get any hints there.&lt;br /&gt;&lt;br /&gt;2. If you see a 403 forbidden error, make sure you have permissions set correctly. I'm running Nginx as www-data and I've set the group/user owners of my rails app to match using the chown -R www-data:www-data command.  It doesn't hurt to confirm it.&lt;br /&gt;&lt;br /&gt;3. Try running your rails app in development mode using the standard script/server.  If it doesn't work there then it obviously won't work in production mode either&lt;br /&gt;&lt;br /&gt;For help, you should check out the great &lt;a href="http://railsforum.com/"&gt;railsforum&lt;/a&gt; or &lt;a href="http://www.ruby-forum.com/"&gt;Mailing list&lt;/a&gt; front-end.&lt;br /&gt;&lt;br /&gt;&lt;/span&gt;&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/689869310107675036-2019862065766599625?l=www.hackido.com'/&gt;&lt;/div&gt;&lt;img src="http://feeds.feedburner.com/~r/Hackido/~4/nQ6K9AvU7TM" height="1" width="1"/&gt;</description><link>http://feedproxy.google.com/~r/Hackido/~3/nQ6K9AvU7TM/install-ruby-on-rails-on-ubuntu-karmic.html</link><author>noreply@blogger.com (vince wadhwani)</author><media:thumbnail xmlns:media="http://search.yahoo.com/mrss/" url="http://2.bp.blogspot.com/_xyjRMd2gFJo/STb6O5fWtwI/AAAAAAAAACI/WfvhPhSAEuE/s72-c/rails.jpg" height="72" width="72" /><thr:total xmlns:thr="http://purl.org/syndication/thread/1.0">5</thr:total><feedburner:origLink>http://www.hackido.com/2009/11/install-ruby-on-rails-on-ubuntu-karmic.html</feedburner:origLink></item><item><guid isPermaLink="false">tag:blogger.com,1999:blog-689869310107675036.post-7261350317049301855</guid><pubDate>Sun, 01 Nov 2009 16:12:00 +0000</pubDate><atom:updated>2009-11-01T13:48:45.900-05:00</atom:updated><category domain="http://www.blogger.com/atom/ns#">bluetooth</category><category domain="http://www.blogger.com/atom/ns#">android</category><title>Review: SE HBH-IS800Z Bluetooth Headset for Android</title><description>&lt;a onblur="try {parent.deselectBloggerImageGracefully();} catch(e) {}" href="http://c1.neweggimages.com/ProductImageCompressAll200/75-975-105-01.jpg"&gt;&lt;img style="float:left; margin:0 10px 10px 0;cursor:pointer; cursor:hand;width: 180px; height: 135px;" src="http://c1.neweggimages.com/ProductImageCompressAll200/75-975-105-01.jpg" border="0" alt="" /&gt;&lt;/a&gt;A few months ago I noticed that my Android G1 phone mic didn't work when I used it through a wired headset.  It's an unusual problem since the USB jack performs all its other functions well: mounting the harddisk, listening to music, charging, etc. But when said headset was plugged in, I could hear phone calls but not speak to the person on the other end.  A secondary purchase revealed the issue was with the phone not the headset. I needed another solution if I was going to talk hands free&lt;br /&gt;&lt;br /&gt;&lt;a onblur="try {parent.deselectBloggerImageGracefully();} catch(e) {}" href="http://thumbs4.ebaystatic.com/pict/3003625112878080_1.jpg"&gt;&lt;img style="float:left; margin:0 10px 10px 0;cursor:pointer; cursor:hand;width: 80px; height: 60px;" src="http://thumbs4.ebaystatic.com/pict/3003625112878080_1.jpg" border="0" alt="" /&gt;&lt;/a&gt;A little while later I found a small bluetooth adapter on eBay. It was small enough but broke in a about two weeks.  I needed a different solution which is when I ran into this &lt;a href="http://www.sonystyle.com/webapp/wcs/stores/servlet/ProductDisplay?catalogId=10551&amp;storeId=10151&amp;langId=-1&amp;productId=8198552921665905560"&gt;Sony Bluetooth Headset&lt;/a&gt;&lt;br /&gt;&lt;br /&gt;&lt;span class="fullpost"&gt;&lt;br /&gt;In a nutshell, this thing works incredibly well.  Previously, I had blamed all my bluetooth woes on the Android software itself, but after using this new headset, I can see that Android is fine as long as you give it decent hardware.&lt;br /&gt;&lt;br /&gt;&lt;span style="font-weight:bold;"&gt;Things to Like&lt;/span&gt;&lt;br /&gt;1. The first thing I love about this headset is that it's small.  There's just a single thin wire that connects the right and left earpieces. The bluetooth and mic are small and hidden.  Charging the headset is also pretty cool with the adapter plugging in directly to the right earpiece (read the manual.. it's a bit sneaky but very nifty)&lt;br /&gt;&lt;br /&gt;2. The quality of the audio is also great.  I'm a big fan of passive noise cancellation so the fact that the earbuds insulate me from ambient noise is wonderful. They're comfortable as well so no complaints there.&lt;br /&gt;&lt;br /&gt;3. The ability to use and not use the headset also works really well.  After the initial pairing, you'll find you just need to turn the headset on and enable bluetooth on your phone and it'll pair quickly and automatically.  This beats opening up the bluetooth settings and scanning for your device any day.. something I had to endure with my previous bluetooth device.&lt;br /&gt;&lt;br /&gt;&lt;span style="font-weight:bold;"&gt;Things not to like&lt;/span&gt;&lt;br /&gt;There's not much to dislike with this headset.  Buying it from Amazon will run you about $110 which is reasonable compared to comparable in-ear headsets that don't have bluetooth.  But here's a list of some minor gripes&lt;br /&gt;&lt;br /&gt;1. You can only use this through bluetooth.  Looking at the image should have given you a warning about that but in case you didn't realize.. you aren't going to be plugging these into your 1985 walkman.&lt;br /&gt;&lt;br /&gt;2. You can only pair with one device at a time.  Largely due to the automatic pairing, it's impossible to associate these headphones to multiple devices.  This is the biggest gripe amongst people who give it a bad review so consider yourself warned!  &lt;br /&gt;&lt;br /&gt;3. There's no way to adjust the audio.  If you have a G1, this is not a big deal since you can easily adjust the volume on the handset even when locked. Other phones, like the iPhone, apparently can't do this. So if you're an iPhone user you'd be best sticking with Apple-blessed accessories.&lt;br /&gt;&lt;br /&gt;&lt;span style="font-weight:bold;"&gt;Things to make you say 'meh'&lt;/span&gt;&lt;br /&gt;I'm neutral about a few things. They're not quite gripes but they are worth mentioning.&lt;br /&gt;&lt;br /&gt;1. The battery life is ok. If you remember to turn it off you can get some good audio time out of it. But if you go on a trip you'll definitely need to bring a charger.&lt;br /&gt;&lt;br /&gt;2. The beauty of the charging interface is that it's unobtrusive.  The downside is you have to have a proprietary charger. When I travel I usually just take a usb cord which I plug into my laptop to charge the phone so this is a small bummer for me.&lt;br /&gt;&lt;br /&gt;&lt;span style="font-weight:bold;"&gt;Conclusion&lt;/span&gt;&lt;br /&gt;I really like these headphones. They are small, light, and provide a great user experience.  If you have a G1 and want a bluetooth headset, you won't be disappointed with these.  &lt;br /&gt;&lt;br /&gt;&lt;span style="font-weight:bold;"&gt;(8/10)&lt;/span&gt;&lt;br /&gt;&lt;br /&gt;&lt;/span&gt;&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/689869310107675036-7261350317049301855?l=www.hackido.com'/&gt;&lt;/div&gt;&lt;img src="http://feeds.feedburner.com/~r/Hackido/~4/mbKKB4juJJs" height="1" width="1"/&gt;</description><link>http://feedproxy.google.com/~r/Hackido/~3/mbKKB4juJJs/review-se-hbh-is800z-bluetooth-headset.html</link><author>noreply@blogger.com (vince wadhwani)</author><thr:total xmlns:thr="http://purl.org/syndication/thread/1.0">0</thr:total><feedburner:origLink>http://www.hackido.com/2009/11/review-se-hbh-is800z-bluetooth-headset.html</feedburner:origLink></item><item><guid isPermaLink="false">tag:blogger.com,1999:blog-689869310107675036.post-5341380453584849580</guid><pubDate>Thu, 29 Oct 2009 14:56:00 +0000</pubDate><atom:updated>2009-10-29T11:06:17.436-04:00</atom:updated><category domain="http://www.blogger.com/atom/ns#">apache2</category><category domain="http://www.blogger.com/atom/ns#">ubuntu</category><title>Quick Tip: Auto enter password for your SSL Certificate in Apache2</title><description>&lt;a onblur="try {parent.deselectBloggerImageGracefully();} catch(e) {}" href="http://3.bp.blogspot.com/_xyjRMd2gFJo/SpYN2SbJ2LI/AAAAAAAAAEg/Rd12_gYq74A/s1600-h/apache.jpg"&gt;&lt;img style="float:left; margin:0 10px 10px 0;cursor:pointer; cursor:hand;width: 172px; height: 197px;" src="http://3.bp.blogspot.com/_xyjRMd2gFJo/SpYN2SbJ2LI/AAAAAAAAAEg/Rd12_gYq74A/s320/apache.jpg" border="0" alt=""id="BLOGGER_PHOTO_ID_5374498431623092402" /&gt;&lt;/a&gt;If you've got an SSL certificate that you're using that happens to be protected with a passphrase, you know that you need to enter that password every single time you restart your web server.  Since Linux is so stable these days it's hardly a big problem, but if something goes wrong while you're on vacation or away from your computer, it could become a big deal.  One solution is to remove the passphrase from your ssl certificate so that Apache doesn't ask you for it.  But there's another way too.&lt;br /&gt;&lt;br /&gt;&lt;span class="fullpost"&gt;&lt;br /&gt;Basically it boils down to creating a file with your passphrase in it and then pointing apache to it.  Since we love Ruby around here, we'll show you how to create the passphrase script using it.&lt;br /&gt;&lt;br /&gt;&lt;pre&gt;#!/usr/bin/ruby&lt;br /&gt;puts "passphrase"&lt;br /&gt;&lt;/pre&gt;&lt;br /&gt;&lt;br /&gt;Save that somewhere and then add this to your /etc/apache2/httpd.conf file:&lt;br /&gt;&lt;br /&gt;&lt;pre&gt;SSLPassPhraseDialog exec:/path/to/passphrase&lt;/pre&gt;&lt;br /&gt;&lt;br /&gt;Lastly, let's make sure that file is executable:&lt;br /&gt;&lt;pre&gt;sudo chmod +x /path/to/passphrase&lt;/pre&gt;&lt;br /&gt;&lt;br /&gt;That should be it.  Let's stop apache and then start it again:&lt;br /&gt;&lt;br /&gt;&lt;pre&gt;sudo apache2ctl stop&lt;br /&gt;sudo apache2ctl start&lt;br /&gt;&lt;/pre&gt;&lt;br /&gt;&lt;br /&gt;If all went well, you weren't asked for a passphrase and your apache server is still running!&lt;br /&gt;&lt;br /&gt;There are some disadvantages though.  One of the biggest reasons to put a passphrase in your ssl cert is to prevent it from being hijacked.  If a cracker can get into your server and take the cert he/she might be also able to get your passphrase file.  That's no good. So be sure to put your passphrase somewhere secure and protect your server.&lt;br /&gt;&lt;/span&gt;&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/689869310107675036-5341380453584849580?l=www.hackido.com'/&gt;&lt;/div&gt;&lt;img src="http://feeds.feedburner.com/~r/Hackido/~4/fCQ7az9sPFU" height="1" width="1"/&gt;</description><link>http://feedproxy.google.com/~r/Hackido/~3/fCQ7az9sPFU/quick-tip-auto-enter-password-for-your.html</link><author>noreply@blogger.com (vince wadhwani)</author><media:thumbnail xmlns:media="http://search.yahoo.com/mrss/" url="http://3.bp.blogspot.com/_xyjRMd2gFJo/SpYN2SbJ2LI/AAAAAAAAAEg/Rd12_gYq74A/s72-c/apache.jpg" height="72" width="72" /><thr:total xmlns:thr="http://purl.org/syndication/thread/1.0">0</thr:total><feedburner:origLink>http://www.hackido.com/2009/10/quick-tip-auto-enter-password-for-your.html</feedburner:origLink></item><item><guid isPermaLink="false">tag:blogger.com,1999:blog-689869310107675036.post-4036863878559969272</guid><pubDate>Sat, 17 Oct 2009 14:35:00 +0000</pubDate><atom:updated>2009-10-17T14:12:07.399-04:00</atom:updated><category domain="http://www.blogger.com/atom/ns#">rails</category><category domain="http://www.blogger.com/atom/ns#">thinking-sphinx</category><category domain="http://www.blogger.com/atom/ns#">sphinx</category><title>Quick Tip: Search for null dates in Thinking Sphinx</title><description>&lt;a onblur="try {parent.deselectBloggerImageGracefully();} catch(e) {}" href="http://2.bp.blogspot.com/_xyjRMd2gFJo/SWket-ab6qI/AAAAAAAAADA/r9-fWP0jJFw/s1600-h/sphinx.jpg"&gt;&lt;img style="float:left; margin:0 10px 10px 0;cursor:pointer; cursor:hand;width: 200px; height: 51px;" src="http://2.bp.blogspot.com/_xyjRMd2gFJo/SWket-ab6qI/AAAAAAAAADA/r9-fWP0jJFw/s320/sphinx.jpg" border="0" alt=""id="BLOGGER_PHOTO_ID_5289793012520184482" /&gt;&lt;/a&gt;In one of my projects, when a record is deleted I set a deleted_at field with the timestamp rather than actually destroying it.  Because that model is indexed by Thinking Sphinx I want to make sure that it doesn't then show up in any search results (the user says she deleted it, right?)  I had thought the way to do that would be as simple as passing an extra condition to my query, but I was wrong.&lt;br /&gt;&lt;br /&gt;&lt;span class="fullpost"&gt;&lt;br /&gt;Instead, what you have to do is create an attribute in your model for the datetime field in question and use :with =&gt; to filter it down.  It might look like this.&lt;br /&gt;&lt;br /&gt;&lt;pre&gt;  # Search Index.&lt;br /&gt;  define_index do&lt;br /&gt;    indexes :name, :sortable =&gt; true&lt;br /&gt;    indexes :description, :sortable =&gt; true&lt;br /&gt;    &lt;br /&gt;    has :deleted_at&lt;br /&gt;&lt;br /&gt;    set_property :delta =&gt; true&lt;br /&gt;  end&lt;br /&gt;&lt;/pre&gt;&lt;br /&gt;&lt;br /&gt;In the above, I'm not indexing deleted_at, rather it's set as an attribute.  When I do my search, I can then use it as follows:&lt;br /&gt;&lt;br /&gt;&lt;pre&gt;Foo.search(params[:search], :with =&gt; {:deleted_at =&gt; 0})&lt;/pre&gt;&lt;br /&gt;&lt;br /&gt;Now why did I use 0 instead of nil?  Because Sphinx equates nil values with 0.. you'll find out about that if you ever decide to sort any integers that involve null values..&lt;br /&gt;&lt;br /&gt;One other thing I want to mention. In my case, I allow admins to search for all the records, including the deleted ones.  If I never wanted those records even indexed I would instead add a where clause to my index itself. ('where "deleted_at IS NOT NULL"') This way I wouldn't have to specify the (:with =&gt;) in my controller.&lt;br /&gt;&lt;br /&gt;&lt;/span&gt;&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/689869310107675036-4036863878559969272?l=www.hackido.com'/&gt;&lt;/div&gt;&lt;img src="http://feeds.feedburner.com/~r/Hackido/~4/tgppu9On6i4" height="1" width="1"/&gt;</description><link>http://feedproxy.google.com/~r/Hackido/~3/tgppu9On6i4/quick-tip-search-for-null-dates-in.html</link><author>noreply@blogger.com (vince wadhwani)</author><media:thumbnail xmlns:media="http://search.yahoo.com/mrss/" url="http://2.bp.blogspot.com/_xyjRMd2gFJo/SWket-ab6qI/AAAAAAAAADA/r9-fWP0jJFw/s72-c/sphinx.jpg" height="72" width="72" /><thr:total xmlns:thr="http://purl.org/syndication/thread/1.0">0</thr:total><feedburner:origLink>http://www.hackido.com/2009/10/quick-tip-search-for-null-dates-in.html</feedburner:origLink></item><item><guid isPermaLink="false">tag:blogger.com,1999:blog-689869310107675036.post-5484579881901827252</guid><pubDate>Wed, 14 Oct 2009 03:57:00 +0000</pubDate><atom:updated>2009-10-14T00:08:28.284-04:00</atom:updated><category domain="http://www.blogger.com/atom/ns#">pulseaudio</category><category domain="http://www.blogger.com/atom/ns#">karmic</category><category domain="http://www.blogger.com/atom/ns#">wine</category><category domain="http://www.blogger.com/atom/ns#">ubuntu</category><title>Quick Tip: Solve skipping audio in Wine</title><description>&lt;a onblur="try {parent.deselectBloggerImageGracefully();} catch(e) {}" href="http://2.bp.blogspot.com/_xyjRMd2gFJo/StVN3xybNHI/AAAAAAAAAEo/cpgVfEvQJuQ/s1600-h/wine.png"&gt;&lt;img style="float:left; margin:0 10px 10px 0;cursor:pointer; cursor:hand;width: 147px; height: 94px;" src="http://2.bp.blogspot.com/_xyjRMd2gFJo/StVN3xybNHI/AAAAAAAAAEo/cpgVfEvQJuQ/s320/wine.png" border="0" alt=""id="BLOGGER_PHOTO_ID_5392301749499016306" /&gt;&lt;/a&gt;If you're using Ubuntu Karmic Koala or Jaunty Jackalope then you may be familiar with Ubuntu's decision to use Pulseaudio to handle sound.  Although there are lots of shortcomings with Pulseaudio, the ability to set different sound levels in different apps seems to be a big win.  Unfortunately, ever since  moving over, my audio performance in wine has been terrible.  It skips, sounds scratchy, and eventually just stops.  Here's how to fix it.&lt;br /&gt;&lt;br /&gt;&lt;span class="fullpost"&gt;&lt;br /&gt;First thing you'll need to do is install a new software source.  Launch the Software sources application and add these two lines:&lt;br /&gt;&lt;br /&gt;&lt;pre&gt;deb http://ppa.launchpad.net/neil-aldur/ppa/ubuntu karmic main &lt;br /&gt;deb-src http://ppa.launchpad.net/neil-aldur/ppa/ubuntu karmic main &lt;br /&gt;&lt;/pre&gt;&lt;br /&gt;&lt;br /&gt;Once done, run this command from terminal to add the correct key&lt;br /&gt;&lt;pre&gt;sudo apt-key adv --keyserver keyserver.ubuntu.com --recv-keys D3E49C82&lt;/pre&gt;&lt;br /&gt;&lt;br /&gt;Finally, update your sources and install a new version of wine.&lt;br /&gt;&lt;pre&gt;sudo apt-get update&lt;br /&gt;sudo apt-get dist-upgrade&lt;br /&gt;sudo apt-get remove wine&lt;br /&gt;sudo apt-get install wine1.2&lt;br /&gt;&lt;/pre&gt;&lt;br /&gt;&lt;br /&gt;Assuming the you have an existing wine app that you run from the .wine directory, simply select "Configure Wine" from the Applications menu.  Click on the Audio tab and unselect whichever current sound driver you are using (probably Alsa or OSS) and instead select the PulseAudio driver.&lt;br /&gt;&lt;br /&gt;If you click Test Sound and hear something then you're good to go!  Quit the winecfg application and go use wine again!  If all goes well, your skipping audio should be gone.  Many thanks to &lt;a href="https://launchpad.net/~neil-aldur"&gt;Neil Wilson&lt;/a&gt; for the good work!&lt;br /&gt;&lt;/span&gt;&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/689869310107675036-5484579881901827252?l=www.hackido.com'/&gt;&lt;/div&gt;&lt;img src="http://feeds.feedburner.com/~r/Hackido/~4/DMKqZhKOHKA" height="1" width="1"/&gt;</description><link>http://feedproxy.google.com/~r/Hackido/~3/DMKqZhKOHKA/quick-tip-solve-skipping-audio-in-wine.html</link><author>noreply@blogger.com (vince wadhwani)</author><media:thumbnail xmlns:media="http://search.yahoo.com/mrss/" url="http://2.bp.blogspot.com/_xyjRMd2gFJo/StVN3xybNHI/AAAAAAAAAEo/cpgVfEvQJuQ/s72-c/wine.png" height="72" width="72" /><thr:total xmlns:thr="http://purl.org/syndication/thread/1.0">1</thr:total><feedburner:origLink>http://www.hackido.com/2009/10/quick-tip-solve-skipping-audio-in-wine.html</feedburner:origLink></item><item><guid isPermaLink="false">tag:blogger.com,1999:blog-689869310107675036.post-2162398264998556842</guid><pubDate>Thu, 27 Aug 2009 04:28:00 +0000</pubDate><atom:updated>2009-08-27T00:39:16.150-04:00</atom:updated><title>Quick Tip: Page caching and POST in Rails</title><description>&lt;a onblur="try {parent.deselectBloggerImageGracefully();} catch(e) {}" href="http://3.bp.blogspot.com/_xyjRMd2gFJo/SpYN2SbJ2LI/AAAAAAAAAEg/Rd12_gYq74A/s1600-h/apache.jpg"&gt;&lt;img style="float:left; margin:0 10px 10px 0;cursor:pointer; cursor:hand;width: 172px; height: 197px;" src="http://3.bp.blogspot.com/_xyjRMd2gFJo/SpYN2SbJ2LI/AAAAAAAAAEg/Rd12_gYq74A/s320/apache.jpg" border="0" alt=""id="BLOGGER_PHOTO_ID_5374498431623092402" /&gt;&lt;/a&gt;I've been playing around with Page Caching as inspired by the New Relic screencasts.  I managed to get my callbacks in place and although I'm still struggling a bit with the flash messages, things are notably better than they were before I started.  One hiccup I ran into though was the fact that page caching was preventing new records from being created in my app.  Why?  Because when I look for a list of products, the request goes to /products (GET) and when I create a new product the request goes to /products (POST).  Apache intercepts both and derails by rails.&lt;br /&gt;&lt;br /&gt;&lt;span class="fullpost"&gt;&lt;br /&gt;The full instructions on page caching that I followed in case anyone is interested are &lt;a href="http://termos.vemod.net/page-caching-with-rails-and-passenger"&gt;right here&lt;/a&gt;.  You'll also want to check out those &lt;a href="http://railslab.newrelic.com/2009/01/22/page-caching"&gt;screencasts&lt;/a&gt;.&lt;br /&gt;&lt;br /&gt;Anyway, to solve it I had to alter the instructions so that POST requests were not cached.  In my /etc/apache2/sites-enabled/ directory, I modified my server entry and added these lines:&lt;br /&gt;&lt;br /&gt;&lt;pre&gt;&lt;br /&gt;        RailsAllowModRewrite On&lt;br /&gt;        RewriteEngine On&lt;br /&gt;&lt;br /&gt;        RewriteCond %{THE_REQUEST} !^POST&lt;br /&gt;        RewriteCond %{REQUEST_URI} ^/([^.]+)$&lt;br /&gt;        RewriteCond %{DOCUMENT_ROOT}/cache/%1.html -f&lt;br /&gt;        RewriteRule ^/[^.]+$ /cache/%1.html [QSA,L]&lt;br /&gt;&lt;br /&gt;        RewriteCond %{DOCUMENT_ROOT}/cache/index.html -f&lt;br /&gt;        RewriteRule ^/$ /cache/index.html [QSA,L]&lt;br /&gt;&lt;/pre&gt;&lt;br /&gt;&lt;br /&gt;This is the one that makes the difference.&lt;br /&gt;&lt;pre&gt;&lt;br /&gt;        RewriteCond %{THE_REQUEST} !^POST&lt;br /&gt;&lt;/pre&gt;&lt;br /&gt;&lt;br /&gt;Ideally, I'd set it to cache just the gets but my apache foo isn't quite up to speed for that so telling it to ignore the posts is what I ended up with.  Hope this saves somebody else some hair pulling.&lt;br /&gt;&lt;/span&gt;&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/689869310107675036-2162398264998556842?l=www.hackido.com'/&gt;&lt;/div&gt;&lt;img src="http://feeds.feedburner.com/~r/Hackido/~4/uAiDaiQswic" height="1" width="1"/&gt;</description><link>http://feedproxy.google.com/~r/Hackido/~3/uAiDaiQswic/quick-tip-page-caching-and-post-in.html</link><author>noreply@blogger.com (vince wadhwani)</author><media:thumbnail xmlns:media="http://search.yahoo.com/mrss/" url="http://3.bp.blogspot.com/_xyjRMd2gFJo/SpYN2SbJ2LI/AAAAAAAAAEg/Rd12_gYq74A/s72-c/apache.jpg" height="72" width="72" /><thr:total xmlns:thr="http://purl.org/syndication/thread/1.0">0</thr:total><feedburner:origLink>http://www.hackido.com/2009/08/quick-tip-page-caching-and-post-in.html</feedburner:origLink></item><item><guid isPermaLink="false">tag:blogger.com,1999:blog-689869310107675036.post-8507875069431307663</guid><pubDate>Sat, 25 Jul 2009 15:58:00 +0000</pubDate><atom:updated>2009-07-25T12:07:30.950-04:00</atom:updated><category domain="http://www.blogger.com/atom/ns#">ruby</category><category domain="http://www.blogger.com/atom/ns#">rails</category><title>Quick Tip: Resource Controller</title><description>&lt;a onblur="try {parent.deselectBloggerImageGracefully();} catch(e) {}" href="http://2.bp.blogspot.com/_xyjRMd2gFJo/STb6O5fWtwI/AAAAAAAAACI/WfvhPhSAEuE/s1600-h/rails.jpg"&gt;&lt;img style="float:left; margin:0 10px 10px 0;cursor:pointer; cursor:hand;width: 90px; height: 115px;" src="http://2.bp.blogspot.com/_xyjRMd2gFJo/STb6O5fWtwI/AAAAAAAAACI/WfvhPhSAEuE/s320/rails.jpg" border="0" alt=""id="BLOGGER_PHOTO_ID_5275679147368560386" /&gt;&lt;/a&gt;If you haven't had a chance to look at &lt;a href="http://github.com/giraffesoft/resource_controller/tree/master"&gt;Resource Controller&lt;/a&gt;, Sean Schofield just put together a nice &lt;a href="http://railsdog.com/2009/07/resource-controller-for-skinny-rails-controllers/"&gt;blog post on it.&lt;/a&gt;  I've played with it a little bit on a recent project and really liked it.  There are some pretty cool permissions things you can do in conjunction with &lt;a href="http://github.com/timcharper/role_requirement/tree/master"&gt;Role Requirement&lt;/a&gt; too.&lt;br /&gt;&lt;br /&gt;&lt;span class="fullpost"&gt;&lt;br /&gt;There's also an &lt;a href="http://www.akitaonrails.com/2008/1/25/easy-restful-rails-screencast"&gt;intro screencast&lt;/a&gt; that he points us to as well. Along with this shorter bit on thin controllers from RailsEnvy:&lt;br /&gt;&lt;br /&gt;&lt;object width="400" height="225"&gt;&lt;param name="allowfullscreen" value="true" /&gt;&lt;param name="allowscriptaccess" value="always" /&gt;&lt;param name="movie" value="http://vimeo.com/moogaloop.swf?clip_id=1050762&amp;amp;server=vimeo.com&amp;amp;show_title=1&amp;amp;show_byline=1&amp;amp;show_portrait=0&amp;amp;color=&amp;amp;fullscreen=1" /&gt;&lt;embed src="http://vimeo.com/moogaloop.swf?clip_id=1050762&amp;amp;server=vimeo.com&amp;amp;show_title=1&amp;amp;show_byline=1&amp;amp;show_portrait=0&amp;amp;color=&amp;amp;fullscreen=1" type="application/x-shockwave-flash" allowfullscreen="true" allowscriptaccess="always" width="400" height="225"&gt;&lt;/embed&gt;&lt;/object&gt;&lt;p&gt;&lt;a href="http://vimeo.com/1050762"&gt;MVC Public Service Announcement #1 : Controller Obesity&lt;/a&gt; from &lt;a href="http://vimeo.com/user496766"&gt;EnvyAds&lt;/a&gt; on &lt;a href="http://vimeo.com"&gt;Vimeo&lt;/a&gt;.&lt;/p&gt;&lt;br /&gt;&lt;/span&gt;&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/689869310107675036-8507875069431307663?l=www.hackido.com'/&gt;&lt;/div&gt;&lt;img src="http://feeds.feedburner.com/~r/Hackido/~4/Se1aX7jRtS0" height="1" width="1"/&gt;</description><link>http://feedproxy.google.com/~r/Hackido/~3/Se1aX7jRtS0/quick-tip-resource-controller.html</link><author>noreply@blogger.com (vince wadhwani)</author><media:thumbnail xmlns:media="http://search.yahoo.com/mrss/" url="http://2.bp.blogspot.com/_xyjRMd2gFJo/STb6O5fWtwI/AAAAAAAAACI/WfvhPhSAEuE/s72-c/rails.jpg" height="72" width="72" /><thr:total xmlns:thr="http://purl.org/syndication/thread/1.0">0</thr:total><feedburner:origLink>http://www.hackido.com/2009/07/quick-tip-resource-controller.html</feedburner:origLink></item><item><guid isPermaLink="false">tag:blogger.com,1999:blog-689869310107675036.post-7919201840128007124</guid><pubDate>Tue, 30 Jun 2009 03:18:00 +0000</pubDate><atom:updated>2009-10-18T11:06:57.096-04:00</atom:updated><category domain="http://www.blogger.com/atom/ns#">gedit</category><category domain="http://www.blogger.com/atom/ns#">plugins</category><category domain="http://www.blogger.com/atom/ns#">rails</category><category domain="http://www.blogger.com/atom/ns#">python</category><title>Recent Update to Gedit Find in Files</title><description>&lt;a onblur="try {parent.deselectBloggerImageGracefully();} catch(e) {}" href="http://3.bp.blogspot.com/_xyjRMd2gFJo/SkmHUtQp3KI/AAAAAAAAAEY/7ffaWUCr6pk/s1600-h/gedit-logo.png"&gt;&lt;img style="float:left; margin:0 0 10px 10px;cursor:pointer; cursor:hand;width: 300px; height: 200px;" src="http://3.bp.blogspot.com/_xyjRMd2gFJo/SkmHUtQp3KI/AAAAAAAAAEY/7ffaWUCr6pk/s320/gedit-logo.png" border="0" alt=""id="BLOGGER_PHOTO_ID_5352958421923126434" /&gt;&lt;/a&gt;I've updated the &lt;a href="http://github.com/vince/find-in-files/downloads"&gt;Find in Files plugin&lt;/a&gt; for Gedit again.  It should be a tiny bit faster and also be able to search special characters.  That means you can search for "&amp;lt;%= link_to" instead of just "%= link_to".  (Characters are now properly escaped.)  The conflict with the Find in Documents plugin should also work.&lt;br /&gt;&lt;br /&gt;The original instructions for using the plugin were on my &lt;a href="http://www.urbanpuddle.com/articles/2008/05/06/introducing-a-new-gedit-plugin-find-in-files"&gt;old site&lt;/a&gt;, but the gist is that you (may) need SnapOpen and need to enable the default File Browser plugin.  Once you enable the File in Files plugin a 3rd tab will appear at the bottom of the screen.  Typing in any search results there will display any matching files under your File Browser root with matching results.  Basically a glorified grep -R &lt;search term&gt;&lt;br /&gt;&lt;br /&gt;&lt;span class="fullpost"&gt;&lt;br /&gt;At some point I may get ambitious and add the ability to exclude log files, but for the moment I'd suggest only searching within a modest scope.  i.e. searching within your Rails App folder? Ok!  Searching within your  Rails Root folder? Not such a great idea because of the potentially large log files and also all the plugins you may have.  You can try it but you've been warned..&lt;br /&gt;&lt;br /&gt;Again, I welcome any contributions or forks, so please have at it.  Gedit plugins are written in Python or C and I don't program either particularly well.&lt;br /&gt;&lt;br /&gt;&lt;a onblur="try {parent.deselectBloggerImageGracefully();} catch(e) {}" href="http://3.bp.blogspot.com/_xyjRMd2gFJo/SkmF9JObxgI/AAAAAAAAAEI/nyRXK4Z9zJo/s1600-h/screenshot1.png"&gt;&lt;img style="float:left; margin:0 10px 10px 0;cursor:pointer; cursor:hand;width: 112px; height: 320px;" src="http://3.bp.blogspot.com/_xyjRMd2gFJo/SkmF9JObxgI/AAAAAAAAAEI/nyRXK4Z9zJo/s320/screenshot1.png" border="0" alt=""id="BLOGGER_PHOTO_ID_5352956917601519106" /&gt;&lt;/a&gt;&lt;a onblur="try {parent.deselectBloggerImageGracefully();} catch(e) {}" href="http://4.bp.blogspot.com/_xyjRMd2gFJo/SkmGI0DB7gI/AAAAAAAAAEQ/gEA9qGSbZQ8/s1600-h/screenshot2.png"&gt;&lt;img style="float:left; margin:0 0 10px 10px;cursor:pointer; cursor:hand;width: 118px; height: 320px;" src="http://4.bp.blogspot.com/_xyjRMd2gFJo/SkmGI0DB7gI/AAAAAAAAAEQ/gEA9qGSbZQ8/s320/screenshot2.png" border="0" alt=""id="BLOGGER_PHOTO_ID_5352957118074973698" /&gt;&lt;/a&gt;&lt;br /&gt;&lt;/span&gt;&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/689869310107675036-7919201840128007124?l=www.hackido.com'/&gt;&lt;/div&gt;&lt;img src="http://feeds.feedburner.com/~r/Hackido/~4/rfB0fSCx2Do" height="1" width="1"/&gt;</description><link>http://feedproxy.google.com/~r/Hackido/~3/rfB0fSCx2Do/recent-update-to-gedit-find-in-files.html</link><author>noreply@blogger.com (vince wadhwani)</author><media:thumbnail xmlns:media="http://search.yahoo.com/mrss/" url="http://3.bp.blogspot.com/_xyjRMd2gFJo/SkmHUtQp3KI/AAAAAAAAAEY/7ffaWUCr6pk/s72-c/gedit-logo.png" height="72" width="72" /><thr:total xmlns:thr="http://purl.org/syndication/thread/1.0">2</thr:total><feedburner:origLink>http://www.hackido.com/2009/06/recent-update-to-gedit-find-in-files.html</feedburner:origLink></item><item><guid isPermaLink="false">tag:blogger.com,1999:blog-689869310107675036.post-5060088542362714117</guid><pubDate>Mon, 29 Jun 2009 19:45:00 +0000</pubDate><atom:updated>2009-06-29T15:55:36.737-04:00</atom:updated><category domain="http://www.blogger.com/atom/ns#">ruby</category><category domain="http://www.blogger.com/atom/ns#">rails</category><title>Validating form_tag in ActiveRecord</title><description>&lt;a onblur="try {parent.deselectBloggerImageGracefully();} catch(e) {}" href="http://2.bp.blogspot.com/_xyjRMd2gFJo/STb6O5fWtwI/AAAAAAAAACI/WfvhPhSAEuE/s1600-h/rails.jpg"&gt;&lt;img style="float:left; margin:0 10px 10px 0;cursor:pointer; cursor:hand;width: 90px; height: 115px;" src="http://2.bp.blogspot.com/_xyjRMd2gFJo/STb6O5fWtwI/AAAAAAAAACI/WfvhPhSAEuE/s320/rails.jpg" border="0" alt=""id="BLOGGER_PHOTO_ID_5275679147368560386" /&gt;&lt;/a&gt;Activerecord valiations are seriously cool. If you just want to validate something in your form it's as easy as specifying the validation in your model and letting Rails take care of the rest.  But what if you want to validate a form_tag?  Generally, we use form_tag when there's no model associated with our form.  Without the model we can't use Activerecord validations!  Well, it turns out there's an elegant solution to the problem thanks to the &lt;a href="http://github.com/kennethkalmer/activerecord-tableless-models/tree/master"&gt;Tableless Activerecord&lt;/a&gt; gem.&lt;br /&gt;&lt;br /&gt;&lt;span class="fullpost"&gt;&lt;br /&gt;Now normally I'm pretty hesitant about adding a gem dependency to my application.  These things tend to break between major rails upgrades and if the plugin developer isn't beholden to thousands of users it could be a while before you see a fix.  In the end, if you're desperate, you could end up maintaining code you hadn't intended to.&lt;br /&gt;&lt;br /&gt;The Tableless Activerecord gem is pretty straight forward though. Even though it hasn't been updated in a year, it seems to work fine with Rails 2.3.2.  Usage is &lt;a href="http://www.opensourcery.co.za/activerecordtableless/"&gt;also pretty simple&lt;/a&gt;.  To validate a contact form without a user model, just create a file called something like contact_messenger.rb and populate with the fields in your contact form and the validates you want:&lt;br /&gt;&lt;br /&gt;&lt;pre&gt;&lt;br /&gt;class ContactMessage &lt; ActiveRecord::Base&lt;br /&gt;&lt;br /&gt;  has_no_table&lt;br /&gt;&lt;br /&gt;  column :name,    :string&lt;br /&gt;  column :email,   :string&lt;br /&gt;  column :phone_number, :string&lt;br /&gt;  column :message, :string&lt;br /&gt;  &lt;br /&gt;  validates_presence_of :name, :email, :message&lt;br /&gt;&lt;br /&gt;end&lt;br /&gt;&lt;/pre&gt;&lt;br /&gt;In the above example, our contact form has fields for name, email, phone number, and message, but we're only requiring name, email, message.  All other validations will work here as well so, for example, if you want to require the phone number be of a particular length you can do that as well.&lt;br /&gt;&lt;br /&gt;Full instructions for using the gem/plugin can be found on &lt;a href="http://www.opensourcery.co.za/activerecordtableless/"&gt;Kenneth Kalmer's website&lt;/a&gt;.&lt;br /&gt;&lt;/span&gt;&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/689869310107675036-5060088542362714117?l=www.hackido.com'/&gt;&lt;/div&gt;&lt;img src="http://feeds.feedburner.com/~r/Hackido/~4/e1gST9RH6Nw" height="1" width="1"/&gt;</description><link>http://feedproxy.google.com/~r/Hackido/~3/e1gST9RH6Nw/validating-formtag-in-activerecord.html</link><author>noreply@blogger.com (vince wadhwani)</author><media:thumbnail xmlns:media="http://search.yahoo.com/mrss/" url="http://2.bp.blogspot.com/_xyjRMd2gFJo/STb6O5fWtwI/AAAAAAAAACI/WfvhPhSAEuE/s72-c/rails.jpg" height="72" width="72" /><thr:total xmlns:thr="http://purl.org/syndication/thread/1.0">2</thr:total><feedburner:origLink>http://www.hackido.com/2009/06/validating-formtag-in-activerecord.html</feedburner:origLink></item><item><guid isPermaLink="false">tag:blogger.com,1999:blog-689869310107675036.post-6719532480180746110</guid><pubDate>Tue, 09 Jun 2009 00:05:00 +0000</pubDate><atom:updated>2009-06-08T20:14:45.800-04:00</atom:updated><title>Quick Tip: Set up a Reverse SSH Tunnel</title><description>&lt;a onblur="try {parent.deselectBloggerImageGracefully();} catch(e) {}" href="http://1.bp.blogspot.com/_xyjRMd2gFJo/Si2pZM99tyI/AAAAAAAAAEA/QmtqKZZiYJo/s1600-h/ssh.jpg"&gt;&lt;img style="float:left; margin:0 10px 10px 0;cursor:pointer; cursor:hand;width: 101px; height: 133px;" src="http://1.bp.blogspot.com/_xyjRMd2gFJo/Si2pZM99tyI/AAAAAAAAAEA/QmtqKZZiYJo/s320/ssh.jpg" border="0" alt=""id="BLOGGER_PHOTO_ID_5345114583201593122" /&gt;&lt;/a&gt;Often times I find myself using ssh to get to a server in order to get a file.  The problem is that my local machine doesn't have its own publicly accessible IP address.  So I end up ssh'ing into the remote server, creating the file I need (e.g. database backup) and then exiting only to run scp from my local machine afterwards.  Plus, if after that I want to erase the file on the remote server I have to ssh in again and tidy up after myself.  That's me running ssh x2 and scp x1 every time I want to accomplish what should be simple.  There's got to be an easier way, right?  You bet..&lt;br /&gt;&lt;br /&gt;&lt;span class ="fullpost"&gt;&lt;br /&gt;First thing you'll want to do is ssh into your server but this time we're going to pass a -R flag and a port number. That flag "Specifies that the given port on the remote (server) host is to be forwarded to the given host and port on the local side." Basically a reverse tunnel..&lt;br /&gt;&lt;br /&gt;&lt;pre&gt;ssh -R 19999:localhost:22 youruser@yourserver.com&lt;/pre&gt;&lt;br /&gt;&lt;br /&gt;Once you're in, you can ssh back to localhost:&lt;br /&gt;&lt;pre&gt;ssh localhost -p 19999&lt;/pre&gt;&lt;br /&gt;&lt;br /&gt;or copy a file down:&lt;br /&gt;&lt;pre&gt;scp -P19999 YOUR_FILE youruser@localhost:/home/youruser/&lt;/pre&gt;&lt;br /&gt;&lt;br /&gt;And that is all there is to it! Credit due to HowTo Forge for pointing the way on this.  They've got a bit more on the topic that you can &lt;a href="http://www.howtoforge.com/reverse-ssh-tunneling"&gt;read about here&lt;/a&gt;.&lt;br /&gt;&lt;br /&gt;&lt;/span&gt;&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/689869310107675036-6719532480180746110?l=www.hackido.com'/&gt;&lt;/div&gt;&lt;img src="http://feeds.feedburner.com/~r/Hackido/~4/J7JNv_Jxd1o" height="1" width="1"/&gt;</description><link>http://feedproxy.google.com/~r/Hackido/~3/J7JNv_Jxd1o/quick-tip-set-up-reverse-ssh-tunnel.html</link><author>noreply@blogger.com (vince wadhwani)</author><media:thumbnail xmlns:media="http://search.yahoo.com/mrss/" url="http://1.bp.blogspot.com/_xyjRMd2gFJo/Si2pZM99tyI/AAAAAAAAAEA/QmtqKZZiYJo/s72-c/ssh.jpg" height="72" width="72" /><thr:total xmlns:thr="http://purl.org/syndication/thread/1.0">1</thr:total><feedburner:origLink>http://www.hackido.com/2009/06/quick-tip-set-up-reverse-ssh-tunnel.html</feedburner:origLink></item><item><guid isPermaLink="false">tag:blogger.com,1999:blog-689869310107675036.post-3237945897385982057</guid><pubDate>Sat, 06 Jun 2009 16:24:00 +0000</pubDate><atom:updated>2009-06-06T12:33:55.112-04:00</atom:updated><category domain="http://www.blogger.com/atom/ns#">rails</category><category domain="http://www.blogger.com/atom/ns#">thinking-sphinx</category><category domain="http://www.blogger.com/atom/ns#">sphinx</category><title>Quick Tip: Search Email in Thinking Sphinx</title><description>&lt;a onblur="try {parent.deselectBloggerImageGracefully();} catch(e) {}" href="http://2.bp.blogspot.com/_xyjRMd2gFJo/SWket-ab6qI/AAAAAAAAADA/r9-fWP0jJFw/s1600-h/sphinx.jpg"&gt;&lt;img style="float:left; margin:0 10px 10px 0;cursor:pointer; cursor:hand;width: 200px; height: 51px;" src="http://2.bp.blogspot.com/_xyjRMd2gFJo/SWket-ab6qI/AAAAAAAAADA/r9-fWP0jJFw/s320/sphinx.jpg" border="0" alt=""id="BLOGGER_PHOTO_ID_5289793012520184482" /&gt;&lt;/a&gt;If you use Sphinx as your search backend you may have noticed that it won't search for an entire email address.  It's a bit perplexing at first since everything else works so well.  After banging my head on the issue for a few hours, I got some direct help from Pat Allan, the creator of Thinking Sphinx.  The problem is with the "@" symbol which is a reserved character in Sphinx. To get around that we need to modify Sphinx's allowable character set.  &lt;br /&gt;&lt;br /&gt;Now for better or for worse, you don't actually need to define any sort of config file by default to use Thinking Sphinx.. it's smart enough to pick sensible defaults.  But in this case we'll have to go ahead and create one.&lt;br /&gt;&lt;br /&gt;&lt;span class = "fullpost"&gt;&lt;br /&gt;Every Ruby on Rails project comes with a config folder where many files you may need to modify are stored.  In this directory create a file called sphinx.yml.  It's a YAML file so be careful about spacing here. It's as sensitive as your database.yml file so if you accidentally alter the spacing things may not work.  &lt;br /&gt;&lt;br /&gt;For our example, let's use the UTF-8 character set.  So in that sphinx.yml file, paste this content:&lt;br /&gt;&lt;br /&gt;&lt;pre&gt;development:&lt;br /&gt;  port: 3312&lt;br /&gt;  charset_table: "0..9, a..z, _, @, A..Z-&gt;a..z, U+410..U+42F-&gt;U+430..U+44F, U+430..U+44F"&lt;br /&gt;test:&lt;br /&gt;  port: 3313&lt;br /&gt;  charset_table: "0..9, a..z, _, @, A..Z-&gt;a..z, U+410..U+42F-&gt;U+430..U+44F, U+430..U+44F"&lt;br /&gt;production:&lt;br /&gt;  port: 3312&lt;br /&gt;  charset_table: "0..9, a..z, _, @, A..Z-&gt;a..z, U+410..U+42F-&gt;U+430..U+44F, U+430..U+44F"&lt;br /&gt;&lt;/pre&gt;&lt;br /&gt;&lt;br /&gt;There are a number of other options you can put in your configuration file of course, but the charset_table one is going to be the one that helps you search email.  In order to see the effect, you'll need to rebuild your index.  If you've got a recent version of the Thinking Sphinx plugin:&lt;br /&gt;&lt;br /&gt;&lt;pre&gt;rake thinking_sphinx:rebuild&lt;/pre&gt;&lt;br /&gt;&lt;br /&gt;Otherwise, you'll need to stop, index, and then start:&lt;br /&gt;&lt;pre&gt;rake thinking_sphinx:stop&lt;br /&gt;rake thinking_sphinx:index&lt;br /&gt;rake thinking_sphinx:start&lt;/pre&gt;&lt;br /&gt;&lt;br /&gt;After that searching for emails should work!&lt;br /&gt;&lt;/span&gt;&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/689869310107675036-3237945897385982057?l=www.hackido.com'/&gt;&lt;/div&gt;&lt;img src="http://feeds.feedburner.com/~r/Hackido/~4/7WDAIZ8deuc" height="1" width="1"/&gt;</description><link>http://feedproxy.google.com/~r/Hackido/~3/7WDAIZ8deuc/quick-tip-search-email-in-thinking.html</link><author>noreply@blogger.com (vince wadhwani)</author><media:thumbnail xmlns:media="http://search.yahoo.com/mrss/" url="http://2.bp.blogspot.com/_xyjRMd2gFJo/SWket-ab6qI/AAAAAAAAADA/r9-fWP0jJFw/s72-c/sphinx.jpg" height="72" width="72" /><thr:total xmlns:thr="http://purl.org/syndication/thread/1.0">0</thr:total><feedburner:origLink>http://www.hackido.com/2009/06/quick-tip-search-email-in-thinking.html</feedburner:origLink></item><item><guid isPermaLink="false">tag:blogger.com,1999:blog-689869310107675036.post-7504405387777940715</guid><pubDate>Thu, 04 Jun 2009 03:31:00 +0000</pubDate><atom:updated>2009-06-04T00:53:38.031-04:00</atom:updated><category domain="http://www.blogger.com/atom/ns#">rails</category><category domain="http://www.blogger.com/atom/ns#">nginx</category><category domain="http://www.blogger.com/atom/ns#">jaunty jackalope</category><category domain="http://www.blogger.com/atom/ns#">ubuntu</category><title>Quick Tip: Nginx and cap deploy:web:disable</title><description>&lt;a onblur="try {parent.deselectBloggerImageGracefully();} catch(e) {}" href="http://2.bp.blogspot.com/_xyjRMd2gFJo/STb6O5fWtwI/AAAAAAAAACI/WfvhPhSAEuE/s1600-h/rails.jpg"&gt;&lt;img style="float:left; margin:0 10px 10px 0;cursor:pointer; cursor:hand;width: 90px; height: 115px;" src="http://2.bp.blogspot.com/_xyjRMd2gFJo/STb6O5fWtwI/AAAAAAAAACI/WfvhPhSAEuE/s320/rails.jpg" border="0" alt=""id="BLOGGER_PHOTO_ID_5275679147368560386" /&gt;&lt;/a&gt;If you've followed my &lt;a href="http://www.hackido.com/2009/04/install-ruby-rails-on-ubuntu-904-jaunty.html"&gt;instructions for installing Ruby on Rails in Ubuntu&lt;/a&gt; you may have felt ambitious and also gotten Capistrano working too.  The only issue is that, by default, nginx doesn't work with Capistrano's web:disable task.  In order to get that working, you'll need to get your system folder setup, add a snippet of code below your server block and then restart nginx.  &lt;br /&gt;&lt;br /&gt;&lt;br /&gt;&lt;br /&gt;&lt;span class="fullpost"&gt;&lt;br /&gt;&lt;span style="font-weight:bold;"&gt;1.&lt;/span&gt; First let's add that snipped of code to nginx.  If you installed nginx via phusion, then your configuration file is in /opt/nginx/conf/nginx.conf.  Use any editor to add these lines within the server{} block:&lt;br /&gt;&lt;br /&gt;&lt;pre&gt;if (-f $document_root/system/maintenance.html) {&lt;br /&gt;   rewrite ^(.*)$ /system/maintenance.html break;&lt;br /&gt;    }&lt;br /&gt;&lt;/pre&gt;&lt;br /&gt;&lt;br /&gt;&lt;span style="font-weight:bold;"&gt;2.&lt;/span&gt; Now that this is done, give nginx a restart:&lt;br /&gt;&lt;br /&gt;&lt;pre&gt;sudo /etc/init.d/nginx stop&lt;br /&gt;sudo /etc/init.d/nginx start&lt;br /&gt;&lt;/pre&gt;&lt;br /&gt;&lt;br /&gt;You can now try disabling the application using the capistrano task:&lt;br /&gt;&lt;br /&gt;&lt;pre&gt;cap deploy:web:disable&lt;/pre&gt;&lt;br /&gt;&lt;br /&gt;&lt;span style="font-weight:bold;"&gt;3.&lt;/span&gt; If you get an error, that says:&lt;br /&gt;&lt;br /&gt;&lt;pre&gt;Net::SFTP::StatusException (Net::SFTP::StatusException open /var/www/my_app/shared/system/maintenance.html (2, "no such file"))&lt;/pre&gt;&lt;br /&gt;&lt;br /&gt;Then you'll need to create a system folder. So log into your remote server and make sure that the you have a system folder with the right permissions setup.&lt;br /&gt;&lt;br /&gt;&lt;pre&gt;mkdir -p /var/www/my_app/shared/system&lt;/pre&gt;&lt;br /&gt;&lt;br /&gt;Try it again:&lt;br /&gt;&lt;br /&gt;&lt;pre&gt;cap deploy:web:disable&lt;/pre&gt;&lt;br /&gt;&lt;br /&gt;If it worked this time then you're done! Just don't forget to enable the server again using:&lt;br /&gt;&lt;br /&gt;&lt;pre&gt;cap deploy:web:enable&lt;/pre&gt;&lt;br /&gt;&lt;br /&gt;Otherwise, be sure to check out the error message (most like a permission issue).  &lt;br /&gt;&lt;br /&gt;&lt;/span&gt;&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/689869310107675036-7504405387777940715?l=www.hackido.com'/&gt;&lt;/div&gt;&lt;img src="http://feeds.feedburner.com/~r/Hackido/~4/h5ZHqJk_SqE" height="1" width="1"/&gt;</description><link>http://feedproxy.google.com/~r/Hackido/~3/h5ZHqJk_SqE/quick-tip-nginx-and-cap.html</link><author>noreply@blogger.com (vince wadhwani)</author><media:thumbnail xmlns:media="http://search.yahoo.com/mrss/" url="http://2.bp.blogspot.com/_xyjRMd2gFJo/STb6O5fWtwI/AAAAAAAAACI/WfvhPhSAEuE/s72-c/rails.jpg" height="72" width="72" /><thr:total xmlns:thr="http://purl.org/syndication/thread/1.0">1</thr:total><feedburner:origLink>http://www.hackido.com/2009/06/quick-tip-nginx-and-cap.html</feedburner:origLink></item><item><guid isPermaLink="false">tag:blogger.com,1999:blog-689869310107675036.post-1112803507576556136</guid><pubDate>Thu, 04 Jun 2009 00:13:00 +0000</pubDate><atom:updated>2009-06-03T23:15:42.157-04:00</atom:updated><category domain="http://www.blogger.com/atom/ns#">rails</category><category domain="http://www.blogger.com/atom/ns#">thinking-sphinx</category><category domain="http://www.blogger.com/atom/ns#">sphinx</category><title>Sum and index a related column in Thinking Sphinx</title><description>&lt;a onblur="try {parent.deselectBloggerImageGracefully();} catch(e) {}" href="http://2.bp.blogspot.com/_xyjRMd2gFJo/SWket-ab6qI/AAAAAAAAADA/r9-fWP0jJFw/s1600-h/sphinx.jpg"&gt;&lt;img style="float:left; margin:0 10px 10px 0;cursor:pointer; cursor:hand;width: 200px; height: 51px;" src="http://2.bp.blogspot.com/_xyjRMd2gFJo/SWket-ab6qI/AAAAAAAAADA/r9-fWP0jJFw/s320/sphinx.jpg" border="0" alt=""id="BLOGGER_PHOTO_ID_5289793012520184482" /&gt;&lt;/a&gt;It's fairly straight forward to get indexing working using the excellent Thinking Sphinx plugin.  But sometimes you may want to do something a little more complicated.  For example, if you have a Model foo with a has_many relationship to model Bar and you want to search on Bar how do you set it up?  Or, what if you want to find out how many Bars Foo has?  Enough! Let's work on an example.&lt;br /&gt;&lt;span class="fullpost"&gt;&lt;br /&gt;Let's start and try to index a User model.  That user has many bank accounts each of which has a balance:&lt;br /&gt;&lt;br /&gt;User 1&lt;br /&gt; --&gt; Account 1 ($5)&lt;br /&gt; --&gt; Account 2 ($100)&lt;br /&gt; --&gt; Account 3 ($3)&lt;br /&gt;&lt;br /&gt;User 2&lt;br /&gt; --&gt; Account 4 ($5)&lt;br /&gt; --&gt; Account 5 ($75)&lt;br /&gt;&lt;br /&gt;In our example, we want to search for users by the amount of cash they have in their accounts.  To do that we need to configure sphinx to first tell it that a User has many Accounts with a bank balance:&lt;br /&gt;&lt;br /&gt;&lt;pre&gt;&lt;br /&gt;class Brigade &lt; ActiveRecord::Base&lt;br /&gt;  has_many :accounts&lt;br /&gt;  &lt;br /&gt;  #sphinx index&lt;br /&gt;  define index do&lt;br /&gt;    has accounts(:bank_balance), :as =&gt; :bank_balance&lt;br /&gt;    indexes "SUM(bank_balance)", :as =&gt; :total_bank_balance, :sortable =&gt; true&lt;br /&gt;  end&lt;br /&gt;end&lt;br /&gt;&lt;/pre&gt;&lt;br /&gt;&lt;br /&gt;With that done, you can now do a search for users with a bank balance of $5 and it will return the 2 users with that balance.  But, you can also do a search for users with a total bank balance of $80 and it will return only user #2.&lt;br /&gt;&lt;br /&gt;&lt;/span&gt;&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/689869310107675036-1112803507576556136?l=www.hackido.com'/&gt;&lt;/div&gt;&lt;img src="http://feeds.feedburner.com/~r/Hackido/~4/hzEd_Agt8kg" height="1" width="1"/&gt;</description><link>http://feedproxy.google.com/~r/Hackido/~3/hzEd_Agt8kg/sum-and-index-related-column-in.html</link><author>noreply@blogger.com (vince wadhwani)</author><media:thumbnail xmlns:media="http://search.yahoo.com/mrss/" url="http://2.bp.blogspot.com/_xyjRMd2gFJo/SWket-ab6qI/AAAAAAAAADA/r9-fWP0jJFw/s72-c/sphinx.jpg" height="72" width="72" /><thr:total xmlns:thr="http://purl.org/syndication/thread/1.0">0</thr:total><feedburner:origLink>http://www.hackido.com/2009/06/sum-and-index-related-column-in.html</feedburner:origLink></item><item><guid isPermaLink="false">tag:blogger.com,1999:blog-689869310107675036.post-8256861240331761909</guid><pubDate>Mon, 01 Jun 2009 00:27:00 +0000</pubDate><atom:updated>2009-05-31T21:00:12.280-04:00</atom:updated><category domain="http://www.blogger.com/atom/ns#">android</category><title>10 little features: Android Cupcake</title><description>&lt;a onblur="try {parent.deselectBloggerImageGracefully();} catch(e) {}" href="http://2.bp.blogspot.com/_xyjRMd2gFJo/STHIGaCBSiI/AAAAAAAAABw/jVrxDzqblP8/s1600-h/android.jpg"&gt;&lt;img style="float:left; margin:0 10px 10px 0;cursor:pointer; cursor:hand;width: 101px; height: 112px;" src="http://2.bp.blogspot.com/_xyjRMd2gFJo/STHIGaCBSiI/AAAAAAAAABw/jVrxDzqblP8/s400/android.jpg" border="0" alt=""id="BLOGGER_PHOTO_ID_5274216651020126754" /&gt;&lt;/a&gt;We've been hearing about Cupcake &lt;a href="http://www.engadget.com/2009/01/23/android-cupcake-in-all-its-keyboard-having-glory-t-mobile-plays/"&gt;for a while&lt;/a&gt; and so the &lt;a href="http://activefrequency.com/blog/2009/15-new-kick-ass-android-cupcake-features/"&gt;feature set&lt;/a&gt; is probably no mystery.  I got tired of waiting for T-mobile to push the update down and so after a few &lt;a href="http://www.engadgetmobile.com/2009/05/22/t-mobile-usa-starts-pushing-android-1-5-to-g1-owners/"&gt;false&lt;/a&gt; &lt;a href="http://www.engadgetmobile.com/2009/05/28/android-1-5-update-for-t-mobile-g1-now-rolling-out-for-real-thi/"&gt;starts&lt;/a&gt; I decided to update myself (instructions &lt;a href="http://www.reddit.com/r/Android/comments/8msiq/sick_of_waiting_for_cupcake_detailed_instructions/c09s3ms"&gt;here&lt;/a&gt;.  After playing around, I found a few things which I thought I'd share in case you hadn't gotten the update yet.  Here are a few of the minor things you've got to look forward to when it does finally come over the air.&lt;br /&gt;&lt;br /&gt;&lt;br /&gt;&lt;span class="fullpost"&gt;&lt;br /&gt;&lt;span style="font-weight:bold;"&gt;1.&lt;/span&gt;  You can now &lt;span style="font-weight:bold;"&gt;mute threads in Gmail&lt;/span&gt;.  This feature is even more handy when you're on the road than when in front of your desktop.  Nothing worse than sitting in the middle of a thread you care nothing about when travelling.  I wonder how Google Wave will handle this..&lt;br /&gt;&lt;br /&gt;&lt;span style="font-weight:bold;"&gt;2.&lt;/span&gt;  &lt;span style="font-weight:bold;"&gt;Most applications will auto-rotate now&lt;/span&gt;.  Auto-rotating had been disabled initially (rumored at Apple's request) but it's now been enabled.  Almost all the apps, from games to the browser take advantage of this.  If you're an app developer be sure to see what your app looks like when in landscape mode...&lt;br /&gt;&lt;br /&gt;&lt;span style="font-weight:bold;"&gt;3.&lt;/span&gt; There's a &lt;span style="font-weight:bold;"&gt;software keyboard with autocomplete&lt;/span&gt; options and you get the ability to enable haptic vibrate response.  T-9 on Android is still not possible due to patent issues, but luckily they've found another way to get the job done.  As you type a small toolbar appears with a number of guesses on what you're typing.  It's pretty effective.  In fact my typing speed on the software keyboard quickly matched how fast I peck using the HTC G1 hardware keyboard.&lt;br /&gt;&lt;br /&gt;&lt;span style="font-weight:bold;"&gt;4.&lt;/span&gt; If you &lt;span style="font-weight:bold;"&gt;hard press the power button it will let you both silence and enable airplane mode&lt;/span&gt; on the phone.  Not much more needs to be said about this. It's nice to have and allowed me to uninstall the ToggleAir application.  &lt;br /&gt;&lt;br /&gt;&lt;span style="font-weight:bold;"&gt;5.&lt;/span&gt;  When you press the any button other than menu and your phone is locked, it will &lt;span style="font-weight:bold;"&gt;show the wallpaper background&lt;/span&gt;.  This helps identify your phone even when locked.  Especially useful if you work in an office with multiple Android phone owners..&lt;br /&gt;&lt;br /&gt;&lt;span style="font-weight:bold;"&gt;6.&lt;/span&gt; When you are on the phone, instead of having the screen black out and the dialpad disappear, it now stays on but makes you &lt;span style="font-weight:bold;"&gt;double tap to access the dialpad&lt;/span&gt;.  Since the G1 doesn't have a hardware proximity sensor like the iPhone, it has no way of knowing when you hold it up to your ear and when you take it down to push a button (Apple really thought of everything didn't they!).  This new behavior tries to do as best as possible given the lack of sensor.&lt;br /&gt;&lt;br /&gt;&lt;span style="font-weight:bold;"&gt;7.&lt;/span&gt; The Email &lt;span style="font-weight:bold;"&gt;IMAP client now really deletes&lt;/span&gt; email from the IMAP server.  If you spent a lot of time on the G1 without using the Google account as your mail email provider, you probably noticed right away that you couldn't really delete emails.  Thankfully, this is now fixed.&lt;br /&gt;&lt;br /&gt;&lt;span style="font-weight:bold;"&gt;8.&lt;/span&gt; Camera improvements:  &lt;span style="font-weight:bold;"&gt;Speed to launch the camera has improved as well as the speed of taking a picture&lt;/span&gt;.  It's almost usable now.. just missing a flash.  Hopefully future Android phones figure this out.  Plus, you can now just hold down the camera button to launch it.  No more going through the app menu and clicking the camera icon..  As covered elsewhere, there is also a camcorder now.&lt;br /&gt;&lt;br /&gt;&lt;span style="font-weight:bold;"&gt;9.&lt;/span&gt; Live folders and widgets:  We've got &lt;span style="font-weight:bold;"&gt;calendar widgets and a live folder&lt;/span&gt; that will launch various things like 'contacts with phone numbers'.  It's a small thing but it does add to the usefulness of the phone.&lt;br /&gt;&lt;br /&gt;&lt;span style="font-weight:bold;"&gt;10.&lt;/span&gt; There are now &lt;span style="font-weight:bold;"&gt;animations when moving between screens&lt;/span&gt; and lots of minor polishing has been done.  You can unlock even more here if you install the "Spare Parts" application from the market.  &lt;br /&gt;&lt;br /&gt;Overall Cupcake is an excellent update.  I'm really looking forward to Donut though.  I especially want the ability to have the phone turn itself on if you have the alarm set.  Google: think of how much energy you would save the world if you enabled this!&lt;br /&gt;&lt;br /&gt;&lt;/span&gt;&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/689869310107675036-8256861240331761909?l=www.hackido.com'/&gt;&lt;/div&gt;&lt;img src="http://feeds.feedburner.com/~r/Hackido/~4/BQfIR2UjMLw" height="1" width="1"/&gt;</description><link>http://feedproxy.google.com/~r/Hackido/~3/BQfIR2UjMLw/little-more-on-android-cupcake.html</link><author>noreply@blogger.com (vince wadhwani)</author><media:thumbnail xmlns:media="http://search.yahoo.com/mrss/" url="http://2.bp.blogspot.com/_xyjRMd2gFJo/STHIGaCBSiI/AAAAAAAAABw/jVrxDzqblP8/s72-c/android.jpg" height="72" width="72" /><thr:total xmlns:thr="http://purl.org/syndication/thread/1.0">0</thr:total><feedburner:origLink>http://www.hackido.com/2009/05/little-more-on-android-cupcake.html</feedburner:origLink></item><item><guid isPermaLink="false">tag:blogger.com,1999:blog-689869310107675036.post-7459202932404806529</guid><pubDate>Thu, 21 May 2009 05:35:00 +0000</pubDate><atom:updated>2009-05-24T22:12:32.075-04:00</atom:updated><category domain="http://www.blogger.com/atom/ns#">android</category><title>Android apps I'm playing with this week</title><description>&lt;a onblur="try {parent.deselectBloggerImageGracefully();} catch(e) {}" href="http://2.bp.blogspot.com/_xyjRMd2gFJo/STHIGaCBSiI/AAAAAAAAABw/jVrxDzqblP8/s1600-h/android.jpg"&gt;&lt;img style="float:left; margin:0 10px 10px 0;cursor:pointer; cursor:hand;width: 101px; height: 112px;" src="http://2.bp.blogspot.com/_xyjRMd2gFJo/STHIGaCBSiI/AAAAAAAAABw/jVrxDzqblP8/s400/android.jpg" border="0" alt=""id="BLOGGER_PHOTO_ID_5274216651020126754" /&gt;&lt;/a&gt;I'm (somewhat) patiently awaiting the cupcake build for my Android phone.  While browsing around the market, I came across a few apps to take for a spin and thought I'd write a short post about them.  Without further delay, here are four apps I kind of liked.&lt;br /&gt;&lt;br /&gt;&lt;span class="fullpost"&gt;&lt;br /&gt;&lt;span style="font-weight:bold;"&gt;1. Contact Owner&lt;/span&gt;:  This is a simple application but incredibly useful.  When you launch it you select some preliminary text, a contact's information, and finally some concluding text.  It will then &lt;span style="font-style:italic;"&gt;display that message on your phone when it's locked&lt;/span&gt;.  Why is that useful?  It's intended for the scenario where you lose your phone and a some kind soul recovers it.  In my case it might say:&lt;br /&gt;&lt;br /&gt;If found, please return to:&lt;br /&gt;Vince Wadhwani: 202-555-1212&lt;br /&gt;Reward if returned.&lt;br /&gt;&lt;br /&gt;Pretty handy, eh?  Sure beats the paper and tape I usually use.&lt;br /&gt;&lt;br /&gt;&lt;span style="font-weight:bold;"&gt;2. Slicehost&lt;/span&gt;: This is an application from the guys at &lt;a href="http://www.slicehost.com"&gt;Slicehost&lt;/a&gt; to help manage your slices.  I have a few slices there so I thought I'd download it and give it a whirl.  The only downside so far is that you have to enable API access on your slice and then manually type the API key into the application.&lt;br /&gt;&lt;br /&gt;Slicehost rarely does anything badly, so I imagine there's a good reason to require the key and not just do it by one-time email/password retrieval. I think the other limitation is that you'll only be able to manage one account at a time which may or may not be a big deal for you depending on how many client slices you manage.&lt;br /&gt;&lt;br /&gt;&lt;span style="font-weight:bold;"&gt;3. Connect Four&lt;/span&gt;:  Yeah, this last one is a softball. I feel it's like tic tac toe and there's no reason to ever lose a round against the computer.  But for whatever reason (concentration is the easiest culprit to blame) it is challenging. Fun too.&lt;br /&gt;&lt;br /&gt;&lt;span style="font-weight:bold;"&gt;4. Spare Parts&lt;/span&gt;:  If you've got cupcake, this is a nice addition.  It allows you to add some features missing from the default options including keyboard animations and haptic responses.  Worth playing with!&lt;br /&gt;&lt;br /&gt;All the above apps are free so unless you're hurting for space I'd say give them a try.&lt;br /&gt;&lt;/span&gt;&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/689869310107675036-7459202932404806529?l=www.hackido.com'/&gt;&lt;/div&gt;&lt;img src="http://feeds.feedburner.com/~r/Hackido/~4/-SCxryC-Kc0" height="1" width="1"/&gt;</description><link>http://feedproxy.google.com/~r/Hackido/~3/-SCxryC-Kc0/android-apps-im-playing-with-this-week.html</link><author>noreply@blogger.com (vince wadhwani)</author><media:thumbnail xmlns:media="http://search.yahoo.com/mrss/" url="http://2.bp.blogspot.com/_xyjRMd2gFJo/STHIGaCBSiI/AAAAAAAAABw/jVrxDzqblP8/s72-c/android.jpg" height="72" width="72" /><thr:total xmlns:thr="http://purl.org/syndication/thread/1.0">0</thr:total><feedburner:origLink>http://www.hackido.com/2009/05/android-apps-im-playing-with-this-week.html</feedburner:origLink></item><item><guid isPermaLink="false">tag:blogger.com,1999:blog-689869310107675036.post-840850828400769751</guid><pubDate>Tue, 05 May 2009 03:23:00 +0000</pubDate><atom:updated>2009-05-05T23:08:07.405-04:00</atom:updated><category domain="http://www.blogger.com/atom/ns#">ruby</category><category domain="http://www.blogger.com/atom/ns#">rails</category><category domain="http://www.blogger.com/atom/ns#">jaunty jackalope</category><category domain="http://www.blogger.com/atom/ns#">ubuntu</category><title>Update your rails stack from Intrepid to Jaunty</title><description>&lt;a onblur="try {parent.deselectBloggerImageGracefully();} catch(e) {}" href="http://3.bp.blogspot.com/_xyjRMd2gFJo/Sf-zcOxJdAI/AAAAAAAAAD4/3bKD5uVO_hs/s1600-h/ubuntu.jpg"&gt;&lt;img style="float:left; margin:0 10px 10px 0;cursor:pointer; cursor:hand;width: 131px; height: 120px;" src="http://3.bp.blogspot.com/_xyjRMd2gFJo/Sf-zcOxJdAI/AAAAAAAAAD4/3bKD5uVO_hs/s320/ubuntu.jpg" border="0" alt=""id="BLOGGER_PHOTO_ID_5332177781411902466" /&gt;&lt;/a&gt;If you've got a Rails Stack built on top of Intrepid Ibex and you want to update it to Jaunty, I've got some good news in that it's pretty easy. Depending on what you have installed though you may need to do a little extra repairing.  Here's a quick step by step detailing my experience.&lt;br /&gt;&lt;br /&gt;&lt;span class="fullpost"&gt;&lt;br /&gt;The first thing you must do is make sure your system is up to date:&lt;br /&gt;&lt;pre&gt;sudo apt-get update&lt;br /&gt;sudo apt-get dist-upgrade&lt;/pre&gt;&lt;br /&gt;&lt;br /&gt;Install any packages that are out of date.  After that, time to get the update manager:&lt;br /&gt;&lt;br /&gt;&lt;pre&gt;sudo apt-get install update-manager-core&lt;/pre&gt;&lt;br /&gt;&lt;br /&gt;Since we're upgrading from Intrepid Ibex to Jaunty Jackalope there shouldn't be a reason to modify any other files like you might when upgraded from the LTS.  So get straight to the matter by running this command:&lt;br /&gt;&lt;br /&gt;&lt;pre&gt;sudo do-release-upgrade&lt;/pre&gt;&lt;br /&gt;&lt;br /&gt;Follow the on-screen instructions. If you're not an advanced user, I'll recommend just taking whatever defaults you are prompted with.  Once you're done, reboot!&lt;br /&gt;&lt;br /&gt;A couple of things went wrong with my upgrade.  First, my Passenger Phusion install went awry. This was 100% my fault though for not upgrading the right way.  Just in case you missed it, follow the instructions on the &lt;a href="http://blog.phusion.nl/2009/04/26/phusion-passenger-222-released/"&gt;official blog&lt;/a&gt;.&lt;br /&gt;&lt;br /&gt;The second thing I needed to fix was my rmagick install.  A key library got removed and so it was back to the drawing board.  Luckily, I found some &lt;a href="http://lovehateubuntu.blogspot.com/2009/04/jaunty-and-rmagick.html"&gt;easy instructions&lt;/a&gt; courtesy of Rob Britton.&lt;br /&gt;&lt;br /&gt;&lt;pre&gt;sudo apt-get install libmagickwand-dev&lt;br /&gt;sudo gem uninstall rmagick&lt;br /&gt;sudo gem install rmagick --no-ri --no-rdoc&lt;/pre&gt;&lt;br /&gt;&lt;br /&gt;And with that you should be done, and hopefully enjoying your upgraded stack.  It also couldn't hurt to do a sudo gem update just in case you have some old crud hanging around.&lt;br /&gt;&lt;br /&gt;&lt;/span&gt;&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/689869310107675036-840850828400769751?l=www.hackido.com'/&gt;&lt;/div&gt;&lt;img src="http://feeds.feedburner.com/~r/Hackido/~4/jeoJGzHr5jg" height="1" width="1"/&gt;</description><link>http://feedproxy.google.com/~r/Hackido/~3/jeoJGzHr5jg/update-your-rails-stack-from-intrepid.html</link><author>noreply@blogger.com (vince wadhwani)</author><media:thumbnail xmlns:media="http://search.yahoo.com/mrss/" url="http://3.bp.blogspot.com/_xyjRMd2gFJo/Sf-zcOxJdAI/AAAAAAAAAD4/3bKD5uVO_hs/s72-c/ubuntu.jpg" height="72" width="72" /><thr:total xmlns:thr="http://purl.org/syndication/thread/1.0">0</thr:total><feedburner:origLink>http://www.hackido.com/2009/05/update-your-rails-stack-from-intrepid.html</feedburner:origLink></item><item><guid isPermaLink="false">tag:blogger.com,1999:blog-689869310107675036.post-8155636504095664428</guid><pubDate>Fri, 24 Apr 2009 18:04:00 +0000</pubDate><atom:updated>2009-04-26T22:59:21.679-04:00</atom:updated><category domain="http://www.blogger.com/atom/ns#">rails</category><title>Quick Tip: Fix RSS feeds in Rails 2.3</title><description>&lt;a onblur="try {parent.deselectBloggerImageGracefully();} catch(e) {}" href="http://2.bp.blogspot.com/_xyjRMd2gFJo/SfIAy74ivmI/AAAAAAAAADw/UwShQmPQvSg/s1600-h/rss.jpg"&gt;&lt;img style="float:left; margin:0 10px 10px 0;cursor:pointer; cursor:hand;width: 127px; height: 85px;" src="http://2.bp.blogspot.com/_xyjRMd2gFJo/SfIAy74ivmI/AAAAAAAAADw/UwShQmPQvSg/s320/rss.jpg" border="0" alt=""id="BLOGGER_PHOTO_ID_5328322184201027170" /&gt;&lt;/a&gt;I saw a sudden drop in the RSS subscribers on one of my site's feeds and it led me to investigate what happened.  Turns out that RSS feeds changed every so slightly in Rails 2.3.  Actually, it might even be a bug.  The symptom is that when you visit your sites rss feed you are prompted to download the file instead of viewing it in an RSS program.  &lt;br /&gt;&lt;br /&gt;&lt;span class="fullpost"&gt;&lt;br /&gt;If you download the file and inspect it, you'll likely see a bunch of stuff that doesn't belong in an RSS feed at all.  Even more confounding is that emptying out your index.rss.builder file still makes your browser download a file.  The culprit is that Rails 2.3 shows the layout file for RSS feeds just like it would for a respond_to html.  To fix it add a render_layout =&gt; false to your controller like so:&lt;br /&gt;&lt;br /&gt;&lt;pre&gt; def index&lt;br /&gt;    @articles = Article.find(:all, :limit =&gt; 8, :order =&gt; 'created_at desc')&lt;br /&gt;    respond_to do |format|&lt;br /&gt;      format.html&lt;br /&gt;      format.rss { render :layout =&gt; false}&lt;br /&gt;      format.xml  { render :xml =&gt; @articles.to_xml }&lt;br /&gt;    end&lt;br /&gt;  end&lt;br /&gt;&lt;/pre&gt;&lt;br /&gt;&lt;br /&gt;Tada!&lt;br /&gt;&lt;/span&gt;&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/689869310107675036-8155636504095664428?l=www.hackido.com'/&gt;&lt;/div&gt;&lt;img src="http://feeds.feedburner.com/~r/Hackido/~4/WcOIQ9W3m3s" height="1" width="1"/&gt;</description><link>http://feedproxy.google.com/~r/Hackido/~3/WcOIQ9W3m3s/quick-tip-fix-rss-feeds-in-rails-23.html</link><author>noreply@blogger.com (vince wadhwani)</author><media:thumbnail xmlns:media="http://search.yahoo.com/mrss/" url="http://2.bp.blogspot.com/_xyjRMd2gFJo/SfIAy74ivmI/AAAAAAAAADw/UwShQmPQvSg/s72-c/rss.jpg" height="72" width="72" /><thr:total xmlns:thr="http://purl.org/syndication/thread/1.0">1</thr:total><feedburner:origLink>http://www.hackido.com/2009/04/quick-tip-fix-rss-feeds-in-rails-23.html</feedburner:origLink></item><item><guid isPermaLink="false">tag:blogger.com,1999:blog-689869310107675036.post-3447103084127087926</guid><pubDate>Mon, 20 Apr 2009 12:56:00 +0000</pubDate><atom:updated>2009-11-07T12:02:49.893-05:00</atom:updated><category domain="http://www.blogger.com/atom/ns#">ruby</category><category domain="http://www.blogger.com/atom/ns#">rails</category><category domain="http://www.blogger.com/atom/ns#">jaunty jackalope</category><category domain="http://www.blogger.com/atom/ns#">ubuntu</category><title>Install Ruby Rails on Ubuntu 9.04 Jaunty Jackalope</title><description>&lt;a onblur="try {parent.deselectBloggerImageGracefully();} catch(e) {}" href="http://2.bp.blogspot.com/_xyjRMd2gFJo/STb6O5fWtwI/AAAAAAAAACI/WfvhPhSAEuE/s1600-h/rails.jpg"&gt;&lt;img style="float:left; margin:0 10px 10px 0;cursor:pointer; cursor:hand;width: 90px; height: 115px;" src="http://2.bp.blogspot.com/_xyjRMd2gFJo/STb6O5fWtwI/AAAAAAAAACI/WfvhPhSAEuE/s320/rails.jpg" border="0" alt=""id="BLOGGER_PHOTO_ID_5275679147368560386" /&gt;&lt;/a&gt;It's getting easier to install Ruby on Rails all the time.  I thought about skipping actually writing this tutorial until I heard that Phusion Passenger 2.2.0 supported Nginx.  I was pretty psyched and so ran off to do an install with that new stack.  If you want a head start on it or need a step by step tutorial then by all means click through for instructions.&lt;br /&gt;&lt;br /&gt;&lt;span style="font-weight:bold;"&gt;Update&lt;/span&gt;: Version for &lt;a href="http://www.hackido.com/2009/11/install-ruby-on-rails-on-ubuntu-karmic.html"&gt;Karmic Koala&lt;/a&gt; now posted.&lt;br /&gt;&lt;br /&gt;&lt;span class="fullpost"&gt;&lt;br /&gt;&lt;script type="text/javascript"&gt;&lt;br /&gt;    if (typeof window.Delicious == "undefined") window.Delicious = {};&lt;br /&gt;    Delicious.BLOGBADGE_DEFAULT_CLASS = 'delicious-blogbadge-line';&lt;br /&gt;&lt;/script&gt;&lt;br /&gt;&lt;script src="http://images.del.icio.us/static/js/blogbadge.js"&gt;&lt;/script&gt;&lt;br /&gt;&lt;b&gt;Step 1&lt;/b&gt;: As usual, the first thing we'll want to do is make sure your version of Ubuntu is up to date.:&lt;br /&gt;&lt;pre&gt;sudo apt-get update&lt;br /&gt;sudo apt-get dist-upgrade&lt;/pre&gt;&lt;br /&gt;&lt;br /&gt;&lt;br /&gt;&lt;b&gt;Step 2:&lt;/b&gt; We'll be installing some software that needs to be built so we'll need to get packages required for compiling. Luckily, you can type this single command and get everything you need:&lt;br /&gt;&lt;pre&gt;sudo apt-get install build-essential&lt;/pre&gt;&lt;br /&gt;&lt;br /&gt;&lt;br /&gt;&lt;b&gt;Step 3:&lt;/b&gt; Once you've got the tools, it's time to install MySQL and Ruby. If you're using SQLite you may not need all this stuff. Otherwise, just copy and paste this command into your terminal if you're in a hurry.&lt;br /&gt;&lt;pre&gt;sudo apt-get install ruby ri rdoc mysql-server libmysql-ruby ruby1.8-dev irb1.8 libdbd-mysql-perl libdbi-perl libmysql-ruby1.8 libmysqlclient15off libnet-daemon-perl libplrpc-perl libreadline-ruby1.8 libruby1.8 mysql-client-5.0 mysql-common mysql-server-5.0 rdoc1.8 ri1.8 ruby1.8 irb libopenssl-ruby libopenssl-ruby1.8 libhtml-template-perl mysql-server-core-5.0&lt;/pre&gt;&lt;br /&gt;If you hadn't previously installed MySQL you'll be asked to set a root password.  You don't have to, of course (it will bug you no fewer than 3 times if you opt not to) but I strongly recommend it.  You'll need this password when you populate your rails config/database.yml file so be sure not to forget it.&lt;br /&gt;&lt;br /&gt;&lt;br /&gt;&lt;b&gt;Step 4:&lt;/b&gt; Grab the latest ruby gems and install them. As always be sure to check &lt;a href="http://rubyforge.org/projects/rubygems/"&gt;rubyforge.org&lt;/a&gt; to make sure you're grabbing the latest one.  As of this writing it's 1.3.4 but it never hurts to confirm.&lt;br /&gt;&lt;pre&gt;wget http://rubyforge.org/frs/download.php/57643/rubygems-1.3.4.tgz&lt;br /&gt;tar xvzf rubygems-1.3.4.tgz&lt;br /&gt;cd rubygems-1.3.4&lt;br /&gt;sudo ruby setup.rb&lt;br /&gt;&lt;/pre&gt;&lt;br /&gt;Once it's done you can remove the .tgz file and erase the rubygems-1.3.4 directory too.  &lt;br /&gt;&lt;br /&gt;&lt;br /&gt;&lt;b&gt;Step 5:&lt;/b&gt; On the command line, type gem -v.  if you get this message we need to make some symlinks:&lt;br /&gt;&lt;br /&gt;&lt;pre&gt;The program 'gem' can be found in the following packages:&lt;br /&gt; * rubygems1.8&lt;br /&gt; * rubygems1.9&lt;br /&gt;Try: sudo apt-get install &lt;selected package&gt;&lt;br /&gt;-bash: gem: command not found&lt;br /&gt;&lt;/pre&gt;&lt;br /&gt;Let's create those symlinks now:&lt;br /&gt;&lt;br /&gt;&lt;pre&gt;sudo ln -s /usr/bin/gem1.8 /usr/local/bin/gem&lt;br /&gt;sudo ln -s /usr/bin/ruby1.8 /usr/local/bin/ruby&lt;br /&gt;sudo ln -s /usr/bin/rdoc1.8 /usr/local/bin/rdoc&lt;br /&gt;sudo ln -s /usr/bin/ri1.8 /usr/local/bin/ri&lt;br /&gt;sudo ln -s /usr/bin/irb1.8 /usr/local/bin/irb&lt;/pre&gt;&lt;br /&gt;&lt;br /&gt;&lt;br /&gt;&lt;b&gt;Step 6:&lt;/b&gt;  Install Ruby on Rails! You can leave off the --no-rdoc and --no-ri switches if you're on a machine with plenty of ram.  But just in case you've got a more modest setup (say 256MB or less) I'd just use the following:&lt;br /&gt;&lt;pre&gt;sudo gem install rails --no-rdoc --no-ri&lt;/pre&gt;&lt;br /&gt;&lt;br /&gt;If you're just doing local development then you are basically done. You may want to install additional gems (such as mongrel).  If you want to deploy Ruby on Rails onto a server then it's time to setup Nginx and Phusion.&lt;br /&gt;&lt;br /&gt;&lt;br /&gt;&lt;b&gt;Step 7:&lt;/b&gt; The folks responsible for Phusion (Hongli Lai &amp; Ninh Bui) have done a remarkable job. They truly understand what it means to make using your product easy for customers.  It's one reason we love Phusion.  Nginx doesn't support loadable modules like Apache does, so Phusion will download, compile, and install it for you.  What could be easier?  To get started, let's download the packages we'll need:&lt;br /&gt;&lt;br /&gt;&lt;pre&gt;sudo apt-get install libc6 libpcre3 libpcre3-dev libpcrecpp0 libssl0.9.8 libssl-dev zlib1g zlib1g-dev lsb-base&lt;/pre&gt;&lt;br /&gt;&lt;br /&gt;&lt;br /&gt;&lt;b&gt;Step 8:&lt;/b&gt; We're going to create a directory for your application.  In anticipation of Capistrano, let's put it in /var/www/myapp/current.  Swap out the myapp with anything you like.&lt;br /&gt;&lt;pre&gt;sudo mkdir -p /var/www/myapp/current&lt;/pre&gt;&lt;br /&gt;If you've got an existing Rails application, it doesn't hurt to populate that directory now.  Just make sure that the root to the public directory is /var/www/myapp/current/public.  Don't forget to chown it for www-data:&lt;br /&gt;&lt;br /&gt;&lt;pre&gt;sudo chown -R www-data:www-data /var/www/myapp/current/&lt;/pre&gt;&lt;br /&gt;&lt;br /&gt;&lt;br /&gt;&lt;b&gt;Step 9:&lt;/b&gt; Now it's time to install Phusion Passenger and let it do it's magic.  &lt;span style="font-weight:bold;"&gt;It's critical that you have Phusion Passenger 2.2.1 or greater installed.&lt;/span&gt;  This may not work with 2.2.0.&lt;br /&gt;&lt;br /&gt;&lt;pre&gt;sudo gem install passenger&lt;br /&gt;sudo passenger-install-nginx-module&lt;/pre&gt;&lt;br /&gt;At this point you'll be greeted with two options.  The first will allow Passenger to do all the work while the second, for advanced users, allows you to point Phusion to  your pre-installed Nginx.  We're going to make life easy on ourselves and choose option 1.  I'd also recommend keeping the default path (/opt/nginx).&lt;br /&gt;&lt;br /&gt;The Nginx configuration file (nginx.conf) file is in /opt/nginx/conf/  They've done you the favor of adding the lines you need to get going.  Defining the configuration file is beyond the scope of this tutorial, but I've included a sample file which you can download.  This file assumes your application is in /var/www/myapp/current.&lt;br /&gt;&lt;br /&gt;&lt;a href="http://vince71.googlepages.com/nginx.conf"&gt;Sample nginx.conf file for Ruby on Rails, Nginx, Phusion Passenger.&lt;/a&gt;&lt;br /&gt;&lt;br /&gt;&lt;br /&gt;&lt;b&gt;Step 10:&lt;/b&gt;  Time to make some Nginx tweaks for Ubuntu/Debian.  If you're used to running nginx as installed by Debian or Ubuntu then you might notice that you've lost the familiar way to start and stop nginx.  Gone is &lt;span style="font-style:italic;"&gt;/etc/init.d/nginx stop&lt;/span&gt; and &lt;span style="font-style:italic;"&gt;/etc/init.d/nginx/start&lt;/span&gt;.  To get it back, copy (or &lt;a href="http://vince71.googlepages.com/nginx"&gt;download&lt;/a&gt;) this into a file called nginx in /etc/init.d/ (as root)&lt;br /&gt;&lt;pre&gt;#! /bin/sh&lt;br /&gt;&lt;br /&gt;### BEGIN INIT INFO&lt;br /&gt;# Provides:          nginx&lt;br /&gt;# Required-Start:    $all&lt;br /&gt;# Required-Stop:     $all&lt;br /&gt;# Default-Start:     2 3 4 5&lt;br /&gt;# Default-Stop:      0 1 6&lt;br /&gt;# Short-Description: starts the nginx web server&lt;br /&gt;# Description:       starts nginx using start-stop-daemon&lt;br /&gt;### END INIT INFO&lt;br /&gt;&lt;br /&gt;PATH=/opt/nginx/sbin:/sbin:/bin:/usr/sbin:/usr/bin&lt;br /&gt;DAEMON=/opt/nginx/sbin/nginx&lt;br /&gt;NAME=nginx&lt;br /&gt;DESC=nginx&lt;br /&gt;&lt;br /&gt;test -x $DAEMON || exit 0&lt;br /&gt;&lt;br /&gt;# Include nginx defaults if available&lt;br /&gt;if [ -f /etc/default/nginx ] ; then&lt;br /&gt;        . /etc/default/nginx&lt;br /&gt;fi&lt;br /&gt;&lt;br /&gt;set -e&lt;br /&gt;&lt;br /&gt;case "$1" in&lt;br /&gt;  start)&lt;br /&gt;        echo -n "Starting $DESC: "&lt;br /&gt;        start-stop-daemon --start --quiet --pidfile /opt/nginx/logs/$NAME.pid \&lt;br /&gt;                --exec $DAEMON -- $DAEMON_OPTS&lt;br /&gt;        echo "$NAME."&lt;br /&gt;        ;;&lt;br /&gt;  stop)&lt;br /&gt;        echo -n "Stopping $DESC: "&lt;br /&gt;        start-stop-daemon --stop --quiet --pidfile /opt/nginx/logs/$NAME.pid \&lt;br /&gt;                --exec $DAEMON&lt;br /&gt;        echo "$NAME."&lt;br /&gt;        ;;&lt;br /&gt;  restart|force-reload)&lt;br /&gt;        echo -n "Restarting $DESC: "&lt;br /&gt;        start-stop-daemon --stop --quiet --pidfile \&lt;br /&gt;                /opt/nginx/logs/$NAME.pid --exec $DAEMON&lt;br /&gt;        sleep 1&lt;br /&gt;        start-stop-daemon --start --quiet --pidfile \&lt;br /&gt;                /opt/nginx/logs/$NAME.pid --exec $DAEMON -- $DAEMON_OPTS&lt;br /&gt;        echo "$NAME."&lt;br /&gt;        ;;&lt;br /&gt;  reload)&lt;br /&gt;          echo -n "Reloading $DESC configuration: "&lt;br /&gt;          start-stop-daemon --stop --signal HUP --quiet --pidfile     /opt/nginx/logs/$NAME.pid \&lt;br /&gt;              --exec $DAEMON &lt;br /&gt;          echo "$NAME."&lt;br /&gt;          ;;&lt;br /&gt;      *)&lt;br /&gt;            N=/etc/init.d/$NAME&lt;br /&gt;            echo "Usage: $N {start|stop|restart|reload|force-reload}" &gt;&amp;2&lt;br /&gt;            exit 1   &lt;br /&gt;            ;;&lt;br /&gt;    esac&lt;br /&gt;&lt;br /&gt;    exit 0&lt;br /&gt;&lt;/pre&gt;&lt;br /&gt;&lt;br /&gt;Next, let's set the permissions and make nginx load on a reboot:&lt;br /&gt;&lt;br /&gt;&lt;pre&gt;sudo chmod +x /etc/init.d/nginx&lt;br /&gt;sudo /usr/sbin/update-rc.d -f nginx defaults&lt;/pre&gt;&lt;br /&gt;&lt;br /&gt;Now you should be able to start and stop nginx using the command you're used to:&lt;br /&gt;&lt;br /&gt;&lt;pre&gt;sudo /etc/init.d/nginx start&lt;/pre&gt;&lt;br /&gt;&lt;br /&gt;&lt;br /&gt;&lt;b&gt;Bonus step&lt;/b&gt; In case it's not already installed, let's grab the perquisites and then install the mysql gem.  This will improve performance on your webserver:&lt;br /&gt;&lt;pre&gt;sudo apt-get install libmysqlclient-dev&lt;br /&gt;sudo gem install mysql --no-rdoc --no-ri&lt;br /&gt;&lt;/pre&gt;&lt;br /&gt;&lt;br /&gt;&lt;br /&gt;&lt;b&gt;Troubleshooting&lt;/b&gt;  If things didn't go smoothly, here are some things to check:&lt;br /&gt;&lt;br /&gt;1. There's an error log for nginx in /opt/nginx/logs/  Try looking to see if you get any hints there.&lt;br /&gt;&lt;br /&gt;2. If you see a 403 forbidden error, make sure you have permissions set correctly. I'm running Nginx as www-data and I've set the group/user owners of my rails app to match using the chown -R www-data:www-data command.  It doesn't hurt to confirm it.&lt;br /&gt;&lt;br /&gt;3. Try running your rails app in development mode using the standard script/server.  If it doesn't work there then it obviously won't work in production mode either&lt;br /&gt;&lt;br /&gt;For help, you should check out the great &lt;a href="http://railsforum.com/"&gt;railsforum&lt;/a&gt; or &lt;a href="http://www.ruby-forum.com/"&gt;Mailing list&lt;/a&gt; front-end.&lt;br /&gt;&lt;/span&gt;&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/689869310107675036-3447103084127087926?l=www.hackido.com'/&gt;&lt;/div&gt;&lt;img src="http://feeds.feedburner.com/~r/Hackido/~4/MNaFOSDnWcw" height="1" width="1"/&gt;</description><link>http://feedproxy.google.com/~r/Hackido/~3/MNaFOSDnWcw/install-ruby-rails-on-ubuntu-904-jaunty.html</link><author>noreply@blogger.com (vince wadhwani)</author><media:thumbnail xmlns:media="http://search.yahoo.com/mrss/" url="http://2.bp.blogspot.com/_xyjRMd2gFJo/STb6O5fWtwI/AAAAAAAAACI/WfvhPhSAEuE/s72-c/rails.jpg" height="72" width="72" /><thr:total xmlns:thr="http://purl.org/syndication/thread/1.0">33</thr:total><feedburner:origLink>http://www.hackido.com/2009/04/install-ruby-rails-on-ubuntu-904-jaunty.html</feedburner:origLink></item><item><guid isPermaLink="false">tag:blogger.com,1999:blog-689869310107675036.post-3880624643945474187</guid><pubDate>Sun, 19 Apr 2009 05:32:00 +0000</pubDate><atom:updated>2009-04-20T22:15:23.618-04:00</atom:updated><title>Swapping Control &amp; Alt in Linux</title><description>&lt;a onblur="try {parent.deselectBloggerImageGracefully();} catch(e) {}" href="http://3.bp.blogspot.com/_xyjRMd2gFJo/Seq4Ima8x4I/AAAAAAAAADo/GtK1fvBMz60/s1600-h/tux_win.jpg"&gt;&lt;img style="float:left; margin:0 10px 10px 0;cursor:pointer; cursor:hand;width: 116px; height: 112px;" src="http://3.bp.blogspot.com/_xyjRMd2gFJo/Seq4Ima8x4I/AAAAAAAAADo/GtK1fvBMz60/s320/tux_win.jpg" border="0" alt=""id="BLOGGER_PHOTO_ID_5326271967211079554" /&gt;&lt;/a&gt;More for my own reference and in preparation of me completely gutting my system, I'm posting the contents of my .xmodmaprc file which swaps the left control and alt-keys.  This allows me to use my linux laptop more like I used my mac, with the command key.&lt;br /&gt;&lt;br /&gt;Feel free to copy the contents to a file called .xmodmaprc and run it using the xmodmap command:&lt;br /&gt;&lt;br /&gt;&lt;pre&gt;xmodmap .xmodmaprc&lt;/pre&gt;&lt;br /&gt;&lt;br /&gt;&lt;span class="fullpost"&gt;&lt;br /&gt;&lt;pre&gt;remove Control = Control_L&lt;br /&gt;remove Mod1 = Alt_L&lt;br /&gt;keysym Control_L = Alt_L&lt;br /&gt;keysym Alt_L = Control_L&lt;br /&gt;add Control = Control_L&lt;br /&gt;add Mod1 = Alt_L&lt;br /&gt;&lt;/pre&gt;&lt;br /&gt;&lt;/span&gt;&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/689869310107675036-3880624643945474187?l=www.hackido.com'/&gt;&lt;/div&gt;&lt;img src="http://feeds.feedburner.com/~r/Hackido/~4/kD7Wrl3xyTI" height="1" width="1"/&gt;</description><link>http://feedproxy.google.com/~r/Hackido/~3/kD7Wrl3xyTI/swapping-control-alt-in-linux.html</link><author>noreply@blogger.com (vince wadhwani)</author><media:thumbnail xmlns:media="http://search.yahoo.com/mrss/" url="http://3.bp.blogspot.com/_xyjRMd2gFJo/Seq4Ima8x4I/AAAAAAAAADo/GtK1fvBMz60/s72-c/tux_win.jpg" height="72" width="72" /><thr:total xmlns:thr="http://purl.org/syndication/thread/1.0">0</thr:total><feedburner:origLink>http://www.hackido.com/2009/04/swapping-control-alt-in-linux.html</feedburner:origLink></item><item><guid isPermaLink="false">tag:blogger.com,1999:blog-689869310107675036.post-9122202199786362928</guid><pubDate>Sat, 18 Apr 2009 22:18:00 +0000</pubDate><atom:updated>2009-11-01T12:06:09.020-05:00</atom:updated><category domain="http://www.blogger.com/atom/ns#">rails</category><category domain="http://www.blogger.com/atom/ns#">thinking-sphinx</category><title>Named Scopes and Thinking Sphinx</title><description>&lt;a onblur="try {parent.deselectBloggerImageGracefully();} catch(e) {}" href="http://2.bp.blogspot.com/_xyjRMd2gFJo/SWket-ab6qI/AAAAAAAAADA/r9-fWP0jJFw/s1600-h/sphinx.jpg"&gt;&lt;img style="float:left; margin:0 10px 10px 0;cursor:pointer; cursor:hand;width: 200px; height: 51px;" src="http://2.bp.blogspot.com/_xyjRMd2gFJo/SWket-ab6qI/AAAAAAAAADA/r9-fWP0jJFw/s320/sphinx.jpg" border="0" alt=""id="BLOGGER_PHOTO_ID_5289793012520184482" /&gt;&lt;/a&gt;I'm really not a fan of the Thinking Sphinx conditions syntax. It's different than what I'm used to using in ActiveRecord and has caused me some problems with dates and such.  Instead I use named scopes whenever I can.  For example, in Railfood, a site for &lt;a href="http://www.railfood.com"&gt;locomotive parts&lt;/a&gt;, I use a named scope to show only products that are in stock.  That causes some issues, not only because of all the nil records but because the default number of results returned is 20.&lt;br /&gt;&lt;br /&gt;&lt;span style="font-weight:bold;"&gt;Note that this article is no longer that useful.  Instead of named scopes please look at sphinx scopes.  Article coming soon&lt;/span&gt;.&lt;br /&gt;&lt;br /&gt;&lt;span class="fullpost"&gt;&lt;br /&gt;For example:&lt;br /&gt;&lt;pre&gt;@p =Product.current.search("injector").size &lt;br /&gt;&lt;br /&gt;=&gt; 20 &lt;/pre&gt;&lt;br /&gt;&lt;br /&gt;or&lt;br /&gt;&lt;pre&gt;@p =Product.current.search("123").size &lt;br /&gt;&lt;br /&gt;=&gt; 20 &lt;/pre&gt;&lt;br /&gt;&lt;br /&gt;One of the first gotchas (&lt;a href="http://davidwparker.com/2008/11/13/named_scope-and-thinking-sphinx-gotcha/"&gt;covered here too&lt;/a&gt;) is that if you actually inspect that array you'll see that it's filled with nil.&lt;br /&gt;&lt;br /&gt;&lt;pre&gt;[nil, nil, nil, nil nil,nil, nil, nil, nil nil,nil, nil, nil, nil nil,nil, nil, nil, nil nil,]&lt;/pre&gt;&lt;br /&gt;&lt;br /&gt;To get around it, call the compact method on the array:&lt;br /&gt;&lt;br /&gt;&lt;pre&gt;@p =Product.current.search("injector").compact.size &lt;br /&gt;&lt;br /&gt;=&gt; 0&lt;br /&gt;&lt;/pre&gt;&lt;br /&gt;&lt;br /&gt;The other gotcha here is that if you actually have 20000 records that match "injector" but only 1 of them is current, you'll get zero results.  To work around that you need to increase the maximum amount of results per page:&lt;br /&gt;&lt;br /&gt;&lt;pre&gt;@p =Product.current.search("injector", :per_page =&gt; 20000).compact.size &lt;br /&gt;&lt;br /&gt;=&gt; 1&lt;br /&gt;&lt;/pre&gt;&lt;br /&gt;&lt;br /&gt;But what about pagination?  Thinking Sphinx does give us this, but the fact that both the methods are called :per_page kind of screws things up.  To work around this, just call paginate on your results:&lt;br /&gt;&lt;br /&gt;&lt;pre&gt;@p =Product.current.search("injector",&lt;br /&gt;                   :per_page =&gt; 20000).paginate(:per_page =&gt; 8, :page =&gt; params[:page])&lt;br /&gt;&lt;/pre&gt;&lt;br /&gt;&lt;br /&gt;And that should do it. Of course, depending on how many results you have you may need to up the initial per_page from 20000 to something larger.  This isn't ideal in my humble opinion, but it works for the moment.  Other suggestions are welcome!&lt;br /&gt;&lt;br /&gt;While we're on the subject of Thinking Sphinx, be sure to set :enable_star =&gt; 1 in your index block if you want to use wildcards in your searches.&lt;br /&gt;&lt;/span&gt;&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/689869310107675036-9122202199786362928?l=www.hackido.com'/&gt;&lt;/div&gt;&lt;img src="http://feeds.feedburner.com/~r/Hackido/~4/n15xfp94vUA" height="1" width="1"/&gt;</description><link>http://feedproxy.google.com/~r/Hackido/~3/n15xfp94vUA/named-scopes-and-thinking-sphinx.html</link><author>noreply@blogger.com (vince wadhwani)</author><media:thumbnail xmlns:media="http://search.yahoo.com/mrss/" url="http://2.bp.blogspot.com/_xyjRMd2gFJo/SWket-ab6qI/AAAAAAAAADA/r9-fWP0jJFw/s72-c/sphinx.jpg" height="72" width="72" /><thr:total xmlns:thr="http://purl.org/syndication/thread/1.0">0</thr:total><feedburner:origLink>http://www.hackido.com/2009/04/named-scopes-and-thinking-sphinx.html</feedburner:origLink></item><item><guid isPermaLink="false">tag:blogger.com,1999:blog-689869310107675036.post-1255534898746028502</guid><pubDate>Fri, 10 Apr 2009 02:19:00 +0000</pubDate><atom:updated>2009-04-09T23:01:02.645-04:00</atom:updated><category domain="http://www.blogger.com/atom/ns#">rails</category><category domain="http://www.blogger.com/atom/ns#">testing</category><title>Testing Attachment Fu in Rails Test Unit</title><description>&lt;a onblur="try {parent.deselectBloggerImageGracefully();} catch(e) {}" href="http://2.bp.blogspot.com/_xyjRMd2gFJo/STb6O5fWtwI/AAAAAAAAACI/WfvhPhSAEuE/s1600-h/rails.jpg"&gt;&lt;img style="float:left; margin:0 10px 10px 0;cursor:pointer; cursor:hand;width: 90px; height: 115px;" src="http://2.bp.blogspot.com/_xyjRMd2gFJo/STb6O5fWtwI/AAAAAAAAACI/WfvhPhSAEuE/s320/rails.jpg" border="0" alt=""id="BLOGGER_PHOTO_ID_5275679147368560386" /&gt;&lt;/a&gt;Whether you're using standard Test Unit or &lt;a href="http://www.thoughtbot.com/projects/shoulda/"&gt;Shoulda&lt;/a&gt;, you should be testing models.  But if a User model has to have a Photo, how do you set up a unit test to make sure it passes?  I've read blog posts and forums threads on the issue but never found anything comprehensive enough for a entry-level rails tester to understand.  So, with that in mind, read on for a quick tutorial.&lt;br /&gt;&lt;br /&gt;&lt;span class="fullpost"&gt;&lt;br /&gt;I'm using Shoulda so my tests are geared for that syntax.  If you're using Test Unit, feel free to modify accordingly. The meat of the answer is still the same.&lt;br /&gt;&lt;br /&gt;First of all, let's assume you're in the test/unit/user.rb file doing your unit test.  Your file starts off looking like this:&lt;br /&gt;&lt;pre&gt;require File.join(File.dirname(__FILE__),"..","test_helper")&lt;br /&gt;&lt;br /&gt;class UserTest &lt; ActiveSupport::TestCase&lt;br /&gt;end&lt;br /&gt;&lt;/pre&gt;&lt;br /&gt;&lt;br /&gt;You'll want to add your context block, setup block, and an assertion too.&lt;br /&gt;&lt;br /&gt;&lt;pre&gt;&lt;br /&gt;context "A new user with a valid photo" do&lt;br /&gt; setup do&lt;br /&gt;   @user = User.create(:email =&gt; "test@example.com", :login =&gt; "test", :password =&gt; "password123", :password_confirmation =&gt; "password123")&lt;br /&gt; end&lt;br /&gt;&lt;br /&gt;  should "be a valid user" do&lt;br /&gt;     assert(@user.valid?)&lt;br /&gt;   end&lt;br /&gt;end&lt;br /&gt;&lt;/pre&gt;&lt;br /&gt;&lt;br /&gt;Running the above test won't work if you're requiring a photo because you haven't actually set one up.  To do that you'll have to use create the photo in the test like this:&lt;br /&gt;&lt;pre&gt;&lt;br /&gt;@photo = Photo.create(:uploaded_data =&gt; fixture_file_upload("/files/mugshot.png",'image/png')&lt;br /&gt;&lt;/pre&gt;&lt;br /&gt;&lt;br /&gt;The tricky part is that the fixture_file_upload is a part of ActionController::TestProcess.  So you'll need to include it for it to work.  The final user.rb will therefore look like this:&lt;br /&gt;&lt;br /&gt;&lt;pre&gt;require File.join(File.dirname(__FILE__),"..","test_helper")&lt;br /&gt;&lt;br /&gt;class UserTest &lt; ActiveSupport::TestCase&lt;br /&gt;  include ActionController::TestProcess&lt;br /&gt;  context "A new user with a valid photo" do&lt;br /&gt;    setup do&lt;br /&gt;      @photo = Photo.create(:uploaded_data =&gt; fixture_file_upload("/files/mugshot.png",'image/png'))&lt;br /&gt;      @user = User.create(:email =&gt; "test@example.com", :login =&gt; "test", :password =&gt; "password123", :password_confirmation =&gt; "password123", :photo =&gt; [@photo])&lt;br /&gt;    end&lt;br /&gt;&lt;br /&gt;    should "be a valid user" do&lt;br /&gt;      assert(@user.valid?)&lt;br /&gt;    end&lt;br /&gt;  end&lt;br /&gt;end&lt;br /&gt;&lt;/pre&gt;&lt;br /&gt;&lt;br /&gt;Now when you run your test, it should pass:&lt;br /&gt;&lt;pre&gt;ruby test/unit/user.rb&lt;br /&gt;&lt;br /&gt;Started&lt;br /&gt;.&lt;br /&gt;Finished in 0.196 seconds.&lt;br /&gt;&lt;br /&gt;1 tests, 1 assertions, 0 failures, 0 errors&lt;br /&gt;&lt;/pre&gt;&lt;br /&gt;&lt;br /&gt;A few things to look out for:&lt;br /&gt;&lt;ul&gt;&lt;br /&gt;&lt;li&gt;  - The above assumes a User has many Photos which is why it's photos =&gt; [@photo] and not photo =&gt; @photo.&lt;/li&gt;&lt;br /&gt;&lt;li&gt;  - You'll need to create a file called mugshot.png and put it in the test/fixtures/files directory (which you probably need to create)&lt;/li&gt;&lt;br /&gt;&lt;li&gt;  - I'm using Shoulda, if you use straight test::unit or rspec, you'll need to change things appropriately.&lt;/li&gt;&lt;br /&gt;&lt;li&gt;  - My example also assumes the only things required in your user model is the email, login, password, and photo. Adjust accordingly.&lt;/li&gt;&lt;br /&gt;&lt;/ul&gt;&lt;br /&gt;Hopefully the above works for you.  Now that you're validating attachments correctly there's no reason not to do more testing!&lt;br /&gt;&lt;/span&gt;&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/689869310107675036-1255534898746028502?l=www.hackido.com'/&gt;&lt;/div&gt;&lt;img src="http://feeds.feedburner.com/~r/Hackido/~4/KiTOPULqUkU" height="1" width="1"/&gt;</description><link>http://feedproxy.google.com/~r/Hackido/~3/KiTOPULqUkU/testing-attachment-fu-in-rails-test.html</link><author>noreply@blogger.com (vince wadhwani)</author><media:thumbnail xmlns:media="http://search.yahoo.com/mrss/" url="http://2.bp.blogspot.com/_xyjRMd2gFJo/STb6O5fWtwI/AAAAAAAAACI/WfvhPhSAEuE/s72-c/rails.jpg" height="72" width="72" /><thr:total xmlns:thr="http://purl.org/syndication/thread/1.0">2</thr:total><feedburner:origLink>http://www.hackido.com/2009/04/testing-attachment-fu-in-rails-test.html</feedburner:origLink></item><item><guid isPermaLink="false">tag:blogger.com,1999:blog-689869310107675036.post-6295942308726187041</guid><pubDate>Sun, 29 Mar 2009 18:17:00 +0000</pubDate><atom:updated>2009-03-29T17:18:10.202-04:00</atom:updated><category domain="http://www.blogger.com/atom/ns#">debian</category><category domain="http://www.blogger.com/atom/ns#">xfce</category><title>XFCE 4.6 makes it into Debian Experimental</title><description>&lt;a onblur="try {parent.deselectBloggerImageGracefully();} catch(e) {}" href="http://1.bp.blogspot.com/_xyjRMd2gFJo/Sc-8XUNyP0I/AAAAAAAAADg/vj4nCeWHlUs/s1600-h/xfce.jpg"&gt;&lt;img style="float:left; margin:0 10px 10px 0;cursor:pointer; cursor:hand;width: 96px; height: 96px;" src="http://1.bp.blogspot.com/_xyjRMd2gFJo/Sc-8XUNyP0I/AAAAAAAAADg/vj4nCeWHlUs/s320/xfce.jpg" border="0" alt=""id="BLOGGER_PHOTO_ID_5318676793697386306" /&gt;&lt;/a&gt;After a long long wait, Debian Experimental is finally blessed with XFCE 4.6.  To install it you have to enable the experimental repository.  Put this line in your /etc/apt/sources.list file somewhere:&lt;br /&gt;&lt;br /&gt;&lt;pre&gt;#Debian Experimental&lt;br /&gt;deb http://ftp.debian.org/debian/ experimental main non-free contrib&lt;br /&gt;&lt;/pre&gt;&lt;br /&gt;&lt;br /&gt;&lt;span class = "fullpost"&gt;&lt;br /&gt;Next run an update and upgrade:&lt;br /&gt;&lt;br /&gt;&lt;pre&gt;sudo apt-get update&lt;br /&gt;sudo apt-get dist-upgrade&lt;/pre&gt;&lt;br /&gt;&lt;br /&gt;Finally, grab the XFCE 4.6 packages:&lt;br /&gt;&lt;pre&gt;sudo apt-get install xfce4 -t experimental&lt;/pre&gt;&lt;br /&gt;&lt;br /&gt;There are a &lt;a href="http://www.xfce.org/about/tour"&gt;number of improvements&lt;/a&gt; in XFCE 4.6 but the big winner for me is the multiple selection of icons on the Desktop. Something that other DE (including LXDE) have been doing forever.&lt;br /&gt;&lt;/span&gt;&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/689869310107675036-6295942308726187041?l=www.hackido.com'/&gt;&lt;/div&gt;&lt;img src="http://feeds.feedburner.com/~r/Hackido/~4/ax70WDbLODE" height="1" width="1"/&gt;</description><link>http://feedproxy.google.com/~r/Hackido/~3/ax70WDbLODE/xfce-46-makes-it-into-debian.html</link><author>noreply@blogger.com (vince wadhwani)</author><media:thumbnail xmlns:media="http://search.yahoo.com/mrss/" url="http://1.bp.blogspot.com/_xyjRMd2gFJo/Sc-8XUNyP0I/AAAAAAAAADg/vj4nCeWHlUs/s72-c/xfce.jpg" height="72" width="72" /><thr:total xmlns:thr="http://purl.org/syndication/thread/1.0">0</thr:total><feedburner:origLink>http://www.hackido.com/2009/03/xfce-46-makes-it-into-debian.html</feedburner:origLink></item><item><guid isPermaLink="false">tag:blogger.com,1999:blog-689869310107675036.post-7839977100081838628</guid><pubDate>Sat, 28 Mar 2009 16:57:00 +0000</pubDate><atom:updated>2009-03-29T14:22:56.141-04:00</atom:updated><category domain="http://www.blogger.com/atom/ns#">javascript</category><category domain="http://www.blogger.com/atom/ns#">rails</category><title>Autocomplete associated fields in Rails 2.3</title><description>&lt;a onblur="try {parent.deselectBloggerImageGracefully();} catch(e) {}" href="http://2.bp.blogspot.com/_xyjRMd2gFJo/STb6O5fWtwI/AAAAAAAAACI/WfvhPhSAEuE/s1600-h/rails.jpg"&gt;&lt;img style="float:left; margin:0 10px 10px 0;cursor:pointer; cursor:hand;width: 90px; height: 115px;" src="http://2.bp.blogspot.com/_xyjRMd2gFJo/STb6O5fWtwI/AAAAAAAAACI/WfvhPhSAEuE/s320/rails.jpg" border="0" alt=""id="BLOGGER_PHOTO_ID_5275679147368560386" /&gt;&lt;/a&gt;I recently had to use an autocomplete field and populate the associated form fields depending on the result.  It's not that bad to do using javascript if you know what you're doing.  The last part is the key of course.  It took me a while to figure it out so I thought I'd share.  So if you're using Ruby on Rails and want to pull it off, here's a step by step on how to do it.&lt;br /&gt;&lt;br /&gt;&lt;span class="fullpost"&gt;&lt;br /&gt;First thing you need to do is install the autocomplete plugin for Rails as this functionality was removed from core quite a while ago:&lt;br /&gt;&lt;br /&gt;&lt;pre&gt;ruby script/plugin install auto_complete&lt;/pre&gt;&lt;br /&gt;&lt;br /&gt;In this example we'll be working with a Charity model.  We'll be grabbing the charity name using an autocomplete text box and filling in another field.  &lt;br /&gt;&lt;br /&gt;This assumes you have your form already set up correctly, so first get the text field with autocomplete set up:&lt;br /&gt;&lt;br /&gt;&lt;pre&gt;&lt;%= text_field_with_auto_complete :charity, :name %&gt;&lt;/pre&gt;&lt;br /&gt;&lt;br /&gt;Next, let's observe that field:&lt;br /&gt;&lt;br /&gt;&lt;pre&gt;&lt;%= observe_field 'charity_name', :on =&gt; 'blur', :frequency =&gt; 0.50, :url =&gt; {:action =&gt; 'update_fields'}, :with =&gt; "'name=' + element.value"  %&gt;&lt;/pre&gt;&lt;br /&gt;&lt;br /&gt;In our example we'll set up one more field which we'll have populated.  Let's call it address:&lt;br /&gt;&lt;br /&gt;&lt;pre&gt;&lt;%= f.text_field :address %&gt;&lt;/pre&gt; &lt;br /&gt;&lt;br /&gt;Remember that your field name may vary depending on how your form is setup.  If unsure, use firebug or view the source of your form.&lt;br /&gt;&lt;br /&gt;Lastly, let's get some controller code in the update_fields action.  This is where we call our javascript.&lt;br /&gt;&lt;br /&gt;&lt;pre&gt;&lt;br /&gt;  def update_fields&lt;br /&gt;    @charity = Charity.find_by_name(params[:name])&lt;br /&gt;    if @charity.nil?&lt;br /&gt;      render :nothing =&gt; true&lt;br /&gt;    else&lt;br /&gt;      render :update do |page|&lt;br /&gt;      page['charity_address'].value = @charity.address&lt;br /&gt;    end&lt;br /&gt;  end&lt;br /&gt;&lt;/pre&gt;&lt;br /&gt;&lt;br /&gt;In the above example you can fill in as many associated fields as you'd like. You can also put the above into an RJS.. frankly that might be better but I like to have logic in my models first, then my controllers, and lastly in any views. &lt;br /&gt;&lt;/span&gt;&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/689869310107675036-7839977100081838628?l=www.hackido.com'/&gt;&lt;/div&gt;&lt;img src="http://feeds.feedburner.com/~r/Hackido/~4/4eJfbeffDEQ" height="1" width="1"/&gt;</description><link>http://feedproxy.google.com/~r/Hackido/~3/4eJfbeffDEQ/autocomplete-associated-fields-in-rails.html</link><author>noreply@blogger.com (vince wadhwani)</author><media:thumbnail xmlns:media="http://search.yahoo.com/mrss/" url="http://2.bp.blogspot.com/_xyjRMd2gFJo/STb6O5fWtwI/AAAAAAAAACI/WfvhPhSAEuE/s72-c/rails.jpg" height="72" width="72" /><thr:total xmlns:thr="http://purl.org/syndication/thread/1.0">1</thr:total><feedburner:origLink>http://www.hackido.com/2009/03/autocomplete-associated-fields-in-rails.html</feedburner:origLink></item><item><guid isPermaLink="false">tag:blogger.com,1999:blog-689869310107675036.post-386045321627543280</guid><pubDate>Wed, 18 Mar 2009 15:46:00 +0000</pubDate><atom:updated>2009-03-18T11:50:32.862-04:00</atom:updated><category domain="http://www.blogger.com/atom/ns#">ruby</category><category domain="http://www.blogger.com/atom/ns#">rails</category><category domain="http://www.blogger.com/atom/ns#">testing</category><title>undefined method `use_transactional_fixtures=' in Rails 2.3</title><description>&lt;a onblur="try {parent.deselectBloggerImageGracefully();} catch(e) {}" href="http://2.bp.blogspot.com/_xyjRMd2gFJo/STb6O5fWtwI/AAAAAAAAACI/WfvhPhSAEuE/s1600-h/rails.jpg"&gt;&lt;img style="float:left; margin:0 10px 10px 0;cursor:pointer; cursor:hand;width: 90px; height: 115px;" src="http://2.bp.blogspot.com/_xyjRMd2gFJo/STb6O5fWtwI/AAAAAAAAACI/WfvhPhSAEuE/s320/rails.jpg" border="0" alt=""id="BLOGGER_PHOTO_ID_5275679147368560386" /&gt;&lt;/a&gt;I'm trying to be better about testing these days so when I upgraded to Ruby on Rails 2.3 the other day I was a bit dismayed to be getting errors with my tests.  They went something like this:&lt;br /&gt;&lt;br /&gt;&lt;pre&gt;&lt;br /&gt;undefined method `use_transactional_fixtures='&lt;br /&gt;&lt;/pre&gt;&lt;br /&gt;&lt;br /&gt;Ug. I generated a new Rails 2.3 app to find out what was going on.&lt;br /&gt;&lt;br /&gt;&lt;span class="fullpost"&gt;&lt;br /&gt;Turns out the problem is in the test_helper.rb file.  You'll need to swap out the old class definition with this:&lt;br /&gt;&lt;br /&gt;&lt;pre&gt;class ActiveSupport::TestCase&lt;/pre&gt;&lt;br /&gt;&lt;br /&gt;Once you do that your tests should run again (assuming they did before hand).&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/689869310107675036-386045321627543280?l=www.hackido.com'/&gt;&lt;/div&gt;&lt;img src="http://feeds.feedburner.com/~r/Hackido/~4/wEvHmuBB_n0" height="1" width="1"/&gt;</description><link>http://feedproxy.google.com/~r/Hackido/~3/wEvHmuBB_n0/undefined-method-usetransactionalfixtur.html</link><author>noreply@blogger.com (vince wadhwani)</author><media:thumbnail xmlns:media="http://search.yahoo.com/mrss/" url="http://2.bp.blogspot.com/_xyjRMd2gFJo/STb6O5fWtwI/AAAAAAAAACI/WfvhPhSAEuE/s72-c/rails.jpg" height="72" width="72" /><thr:total xmlns:thr="http://purl.org/syndication/thread/1.0">0</thr:total><feedburner:origLink>http://www.hackido.com/2009/03/undefined-method-usetransactionalfixtur.html</feedburner:origLink></item></channel></rss>
