KZAK: an open source web-based jukebox

Posted by Trevor in General, KZAK on February 08, 2010

I'm happy to announce that I've made my latest side-project open source. It's called KZAK. It's a simple web-based jukebox that you can use to share and listen to music with your friends.

The feature set is pretty limited right, but I hope to continue to improve things over time. I'm already encouraged by how quickly some of my friends have taken to the app, and I think you'll enjoy it - even in this early form.

So far you can:

  • Invite people to use the site via email
  • Upload mp3, mp4, and m4a (iTunes) tracks with an upload queue and progress
  • Listen to the uploaded music as a playlist, even in an inactive browser tab

Like I said, it's pretty basic (invite, upload, listen) but surprisingly functional. Plus, I'm using all kinds of interesting stuff behind the scenes, which is why I really wanted to share the code ;)

To begin with, we've got a Rails app that's using the latest and greatest in user authentication technology: Devise. If you're using something like restful_authentication or Authlogic, I implore you to take a look at Devise. It's a phenomenal improvement from these other two popular options, and it's being actively supported by José Valim, the latest Rails committer. Essentially, it's a Rails Engine that sits on top of Warden - a generalized Rack authentication framework. This combination is extraordinarily flexible and easy to use. It's opinionated (in a good way) while simultaneously doing a good job of staying out of the way. It introduces very little code into your application, and the source is well documented, well tested, and easy to follow. A++ highly recommended.

To handle the file uploads, I've switched from Paperclip to CarrierWave. While Paperclip has (and continues) to serve me well in many applications I work with, I really appreciate the modular approach that CarrierWave takes. It's agnostic as to which of the popular S3 clients you use, supporting both aws/s3 and right_aws. It's also ORM agnostic and not tightly coupled to Active Record. The tight coupling of Paperclip has caused us some grief at work, and I'm also confused about the state of Paperclip's support for aws/s3 and right_aws. So, I was happy to find this new project, and the maintainer Jonas Nicklas seems to be an extremely responsive and helpful dude, which is always good thing. The code looks great, and I've had an easy time working with this library so far.

In concert with CarrierWave, I'm also using the venerable SWFUpload to support upload queues and progress meters. I'm absolutely baffled as to why this kind of thing isn't easy/possible to support without Flash, but here we are. Of course, I have a fallback "regular upload form" that still uses some ajax to make things a little easier. There are a few blog posts and tutorial applications around on GitHub that helped me get SWFUpload working with Rails and jQuery, and I'm happy to put back out an example application that other people can refer to if they're interested in supporting upload queues and/or upload progress meters.

Next, to support audio playback while I work on supporting html5 properly, I'm using the extremely awesome SoundManager 2. Unfortunately, this is another part of the infrastructure using Flash, but the features and functionality of SoundManager are really something special. I've only scratched the surface of what this library can do, but I'm already enjoying it quite a bit. If you're working with jQuery and SoundManager, you may find the KZAK source code worth perusing. You might also take a look at Adrien Gibrat's plugin, which is a cool jQuery plugin that packs a lot of functionality.

Also running in the background of KZAK is a Twitter-style following/unfollowing system that I haven't exposed much of yet. It's basically the same system that's powering Flowcoder. You can check out this example app I made if you're interested in seeing that on its own. Currently, all users in the system follow (and are followed by) all of the other users. I plan to allow for "unfollowing" users some time soon, which will allow for some healthy splintering of the community in the case that you're not interested in everything that everyone is uploading.

Finally - and perhaps best of all - KZAK is fully compatible with and easy to install on Heroku. All you need is an S3 account and you're ready to get started with a web-based jukebox for you and your friends for free.

http://github.com/trevorturk/kzak

Anyway, please feel free to dig around the source code if you're interested in any of this. I think there's a lot of good stuff in there, especially considering that the Ruby portion of the app is clocking in at under ~250 LOC right now. Thanks, open source community ;)

Cloudfront: no-brainer CDN support for S3

Posted by Trevor in General on February 08, 2010

Amazon's CloudFront is a phenomenal addition to their S3 file-hosting service.

Amazon CloudFront is a web service for content delivery. It integrates with other Amazon Web Services to give developers and businesses an easy way to distribute content to end users with low latency, high data transfer speeds, and no commitments.

Amazon CloudFront delivers your static and streaming content using a global network of edge locations. Requests for your objects are automatically routed to the nearest edge location, so content is delivered with the best possible performance. Amazon CloudFront works seamlessly with Amazon Simple Storage Service (Amazon S3) which durably stores the original, definitive versions of your files. Like other Amazon Web Services, there are no contracts or monthly commitments for using Amazon CloudFront – you pay only for as much or as little content as you actually deliver through the service.

If you're using S3 and you're not using CloudFront, you should take a moment to check it out. You'll be surprised at how little work it takes to set up, how much it speeds up your assets serving, and how little it costs.

CloudFront is a part of the Amazon Console now, so it's very easy to set up. All you need to do is to create a distribution, which means enabling CloudFront for a specific S3 bucket and choosing a CNAME that you'll serve your assets from. Then, you need to set up the CNAME in your DNS configuration on GoDaddy and you're done.

The following two screenshots illustrate the process.

Step one is to creating the distribution in Amazon's Console:

Note the Domain Name and CNAMEs sections in the lower half of the screen. I've chosen the CNAME of "s3.kzak.org" because I want my S3 bucket to be aliased such that URLs will look like this:

http://s3.kzak.org/example.jpg

CloudFront has provided me with the domain name that I need to provide to GoDaddy. Since I'm using their "Total DNS" option, all I have to do is add the CNAME like so:

Notice that the CNAME of "s3" is set to the domain name that CloudFront provided me.

These changes seem to take about 30 minutes to percolate through the internets, but that's all it takes to get started with CloudFront.

For bonus points, you may want to read up about using multiple asset hosts in Rails and apply this technique in your applications for additional throughput.

Flowcoder: Share, refactor, and tweet code snippets

Posted by Trevor in General, Ruby/Rails on February 08, 2010

I just realized that I never posts about our entry into the Rails Rumble last year.

Flowcoder: An Evolution of the Code Snippet Site

Coded and designed by @gbuesing, @scottymac, and @trevorturk for @railsrumble in 2009.

Flowcoder has what you would expect from a code snippet side: multiple language support, raw code view, and support for embedding on other sites.

What was missing for us and what we really wanted was a site that featured not just the code, but the people creating the code. Just as we glean interesting tidbits about people's lives from Twitter, we wanted to learn from our favorite coders by being able to follow the kind of code snippets they create. We wanted to share our own code snippets and have others refactoring them: to fix, optimize, and make them better, and learn in the process. And we wanted to be kept informed: when your code is refactored on Flowcoder, you'll see an @reply from @flowcoderbot with some information and a link. This closes the loop in a casual, low bandwidth fashion and highlights the advantage of using Twitter as both an identity and notification system.

Weekly Digest, 2-1-10

Posted by Weekly Digest in Weekly Digest on February 01, 2010

If you enjoy these links, you should follow me on GitHub here.

iPhone / iPad icon PSD template

I’ve decided to work with my good friend, Sean Patrick O‘Brien to create a PSD based off the exact overlays, outlines, and masks the iPhone and iPad OS use to mask icons.

visionmedia's express

Sinatra-like JavaScript node.js web development framework -- insanely fast, insanely sexy

Commit 8ae25 to rails

Introduce class_attribute to declare inheritable class attributes. Writing an attribute on a subclass behaves just like overriding the superclass reader method. Unifies and replaces most usage of cattr_accessor, class_inheritable_attribute, superclass_delegating_attribute, and extlib_inheritable_attribute.

jed's fab

(fab) is a lightweight (~2KB minified and gzipped) toolkit that makes it easy to build asynchronous web apps. It takes advantage of the flexibility of javascript to create a concise DSL without pre-compilation or magic scope hackery.

Static websites with Heroku

I recently moved off of Dreamhost in favor of Heroku. I have a few static sites I needed to move over and here's how I did it...

Future Shock

If the iPad and its successor devices free these people to focus on what they do best, it will dramatically change people's perceptions of computing from something to fear to something to engage enthusiastically with. I find it hard to believe that the loss of background processing isn't a price worth paying to have a computer that isn't frightening anymore.

Hacker News | Tinkerer’s Sunset

The iPad has really brought out a lot of old, crochety "well in my day" engineers that are now to the point where its embarassing. The iPad will draw more people towards software engineering, because for the first time we will have a general purpose computer that doesn't suck horribly for normal people.

Joe Hewitt: iPad

iPad is an incredible opportunity for developers to re-imagine every single category of desktop and web software there is. Seriously, if you're a developer and you're not thinking about how your app could work better on the iPad and its descendants, you deserve to get left behind.

JSLint

The JavaScript Code Quality Tool

jeffkreeftmeijer's navvy at master - GitHub

Simple Ruby background job processor inspired by delayed_job, but aiming for database agnosticism.

iPad: an Apple for Mom

Most people have a computer at home. For some (like my mom), it’s an ancient Dell laptop they bought years ago. Others have bought into the netbook trend and invested a small amount of money into a machine that, for most people, can only be irritating to use (slow, small, ugly, and burns your lap – not a recipe for success). A few have actually paid good money for what was supposed to be a modern machine, and actually turned out to be yet another annoying slow, painful-to-use, Windows-based machine infested with trial software, spyware, and sometimes viruses.

documentcloud's underscore

Functional Programming Aid for Javascript. Works well with jQuery.

neerajdotname's admin_data

Browse and Manage your data using browser

In praise of git’s index

The key to understanding it is how it interacts with git diff. Once you add something to the index (also referred to as staging it), it disappears off the diff. You can pass --cached to see what changes you have staged, but by default, it doesn’t show you the changes that you have asserted are ready for commit.

jnicklas's capybara

webrat alternative which aims to support all browser simulators

thoughtbot's pacecar

Generated scopes for ActiveRecord classes

quirkey's sammy

Sammy is a tiny javascript framework built on top of jQuery, It's RESTful Evented Javascript.

New ActionMailer API in Rails 3.0

Action Mailer has long been the black sheep of the Rails family. Somehow, through many arguments, you get it doing exactly what you want. But it takes work! Well, we just fixed that. Action Mailer now has a new API.

Stanford's Entrepreneurship Corner: David Heinemeier Hansson, 37signals - Unlearn Your MBA

David Heineimeier Hansson, the creator of Ruby on Rails and partner at 37signals in Chicago, says that planning is guessing, and for a start-up, the focus must be on today and not on tomorrow. He argues that constraints--fiscal, temporal, or otherwise--drive innovation and effective problem-solving. The most important thing, Hansson believes, is to make a dent in the universe with your company.

Bumps ahead as Vimeo, YouTube respond to HTML5 video demand

Although there are still a number of important problems to solve before open video can displace Flash-based video playback on the Web, it seems likely that we will see more progress now that the major players are all on board and the users are enthusiastically calling for better standards support.

Discovering Rails 3 generators

This weekend during Rails Bugmash I stumbled across some nice posts about Rails 3 generators which motivated me to share them and add some comments!

Active Record Query Interface 3.0

I’ve been working on revamping the Active Record query interface for the last few weeks ( while taking some time off in India from consulting work, before joining 37signals ), building on top of Emilio’s GSOC project of integrating ARel and ActiveRecord. So here’s an overview of how things are going to work in Rails 3.

Show and Sell: The Secret to Apple's Magic

Flash an exotic prototype, then—Presto!—get people to buy your more boring stuff. That kind of thinking still rules at most electronics companies. Apple under Steve Jobs only shows off actual products. The difference? Apple's arcane secret to success.

omgbloglol Rails 3 Introduction

This post is kicking off a series that I’m doing about moving your skills and migrating your code to Rails 3. I’ll be sharing some practical insights and covering some pretty in-depth topics as we go along (I’ve got some notes for entries about upgrading plugins, taking advantage of new features like the agnosticism, migrating applications, and so on), but before I go into a lot of specifics, I thought it might be useful to go over some of the high-level philosophical and architectural changes that have gone on in the Rails code between versions 2 and 3.

How A Spare Computer Became Twitpic

In 2008, Noah Everett wanted to share photos on Twitter. Since there was no way to do it, he grabbed an old server and created Twitpic as a side project... A $1.5+ Million A Year Twitter Success Story...

API_Cheatsheet - Couchdb Wiki

chartbeat

The web doesn't work with a 24-hour lag and neither should your analytics. Chartbeat gives you real-time analytics so that you know what's happening when it's happening. Control the story, track a product launch, exploit an opportunity from the moment they happen.

The Concept *is* the Execution

You cannot design a great service without an obsessional focus on the details.

Graffiti Analysis

Graffiti Analysis is an extensive ongoing study in the motion of graffiti. Custom software designed for graffiti writers creates visualizations of the often unseen motion involved in the creation of a tag.

How I solved email overload using gmail

It's simple. Every single email that arrives in my in-box is immediately put in a filter.

Weekly Digest, 1-6-09

Posted by Weekly Digest in Weekly Digest on January 06, 2010

If you enjoy these links, you should follow me on GitHub here.

Steve Krug on Usability

I can’t think of a better intro to the essential points of usability than this presentation by Steve Krug. I especially appreciate his “least you can do” approach. Enjoy.

iBusted

...the Sun-Times is forwarding every page request to http://mobile.suntimes.com (the root “home page” of the optimized site), thus breaking every link to every single article they’ve published. This is the very definition of a broken website.

Caliper: Hosted Ruby Metrics

Ruby metrics don't get any easier than this.

Admin Noob

System Administration for Noobs

AJAX activity indicators

An important design element that’s part of the whole AJAX business is somehow letting your user know that stuff is actually happening while the server crunches away. A common way to do so, is to add a little animated GIF that is only shown when the AJAX request is happening.

The Ruby Toolbox

The Ruby Toolbox gives you an overview of these tools, sorted in categories and rated by the amount of watchers and forks in the corresponding source code repository on GitHub so you can find out easily what options you have and which are the most common ones in the Ruby community.

Waging War on Whitespace (using TextMate)

To avoid diff cruft you’ll need to instruct your text editor to remove trailing whitespace, preferably every time you save so you don’t have to remember to do it.

roman's warden_oauth

warden_oauth enhances the Warden authentication framework, offering a simple interface for creating oauth strategies.

ffmike's has_messages

This plugin provides a nice and easy way to create simple internal messaging system in your application.

jpignata's temping

Temping allows you to create arbitrary ActiveRecord models backed by a temporary SQL table for use in tests.

Gem Bundler is the Future

This guide went over how to use Bundler today, with a Rails 2.3.4 app. According to Yehuda, this eventually will be packaged in Rails 3, so the commands will be baked into Rails…so something like script/bundle. The nice thing is that you can use the bundler with any Ruby project, so this is good to know in general.

tipsy

Tipsy is a jQuery for creating a Facebook-like tooltips effect based on an anchor tag's title attribute.

One in Three: Inherited Resources, Has Scope and Responders

So we were there, building an application based on scaffold, and as we saw duplicated code we started to realize Inherited Resources contains a lot of tools that could be used outside its context. And this is what is happening right now, two new gems are being launched: Responders and HasScope.

Why programmers are not paid in proportion to their productivity

The romantic image of an über-programmer is someone who fires up Emacs, types like a machine gun, and delivers a flawless final product from scratch. A more accurate image would be someone who stares quietly into space for a few minutes and then says “Hmm. I think I’ve seen something like this before.”

Learn to Let Go: How Success Killed Duke Nukem

It’s a dilemma all artists confront, of course. When do you stop creating and send your work out to face the public? Plenty of Hollywood directors have delayed for months, dithering in the editing room. But in videogames, the problem is particularly acute, because the longer you delay, the more genuinely antiquated your product begins to look — and the more likely it is that you’ll need to rip things down and start again. All game designers know this, so they pick a point to stop improving — to “lock the game down” — and then spend a frantic year polishing. But Broussard never seemed willing to do that.

jzawodn's mytop

a "top" clone for MySQL

Why I think Mongo is to Databases what Rails was to Frameworks // RailsTips by John Nunemaker

Below are 7 Mongo and MongoMapper related features that I have found to be really awesome while working on switching Harmony, a new website management system by my company, Ordered List, to Mongo from MySQL.

Server-Side Javascript: Back With a Vengeance

Last month was Javascript season in Europe, with two conferences dedicated to the language that powers interactive web applications, and a third, which featured it heavily. If a common theme emerged, it was the buzz about Javascript leaping out of the browser to serve other domains, and the noise has only become louder in the aftermath.

Subdomains and sessions to the rescue!

After some research we decided to go with the subdomain-fu gem, which is great to give your application the ability of handling subdomains. Another great resource we have used is Ryan Bates’ screencast about the subject. But they did not solve our problem completely, so here we are going to document a few steps to help you get up and running easily with subdomains and sessions.

CodeRack: Rack::Snapshot

Rack::Snapshot is a quick way to expand image urls for the popular image sharing services. If you have a URL to a public page for an image on Skitch, Img.ly, Twitpic, Yfrog, Flickr, or Twitgoo, this middleware will embed the direct image URL for you.

config/deploy.rb from tobi's imagery

Capistrano tasks for a GitHub-style deployment.

sickill's racksh

Console for any Rack based ruby web app.

tobi's clarity

Web interface for the grep and tail -f unix tools. Useful for real-time log analysis. Remotely related to splunk.

tobi's imagery

Image server / proxy that can resize images on demand based on common file prefixes ( such as _small, _medium ) and apply other rmagick effects. Supposed to be used between a Squid/Varnish and S3.

Introducing RR

I'm pleased to introduce a new Test Double (or mock) framework named RR, which is short for Double Ruby.

Weekly Digest, 12-11-09

Posted by Weekly Digest in Weekly Digest on December 11, 2009

This time I have an excuse for the non-weekly nature of the weekly digest... I've been traveling! Please do check out some photos if you're interested on that sort of thing.

Video of Node.js by Ryan Dahl at JSConf.eu

Node.js might be the most exciting single piece of software in the current JavaScript universe. Ryan received standing ovations for his talk and he really deserved it!

How to Begin Playing With Rails 3

Curious to take a look at Rails 3?

Lawnchair

Sorta like a couch except smaller and outside, also, a client side JSON document store. Perfect for webkit mobile apps that need a lightweight, simple and elegant persistence solution.

stupid ruby tricks

Over the past few months of slinging Ruby here at Thoughtbot, I’ve picked up quite a few stupid ruby tricks smart ruby techniques that really help out your code.

Vanity: Experiment Driven Development for Rails

You’ve got your TDD, your BDD, your load testing, your user testing, your code metrics. All tools for testing your code and improving it. Here’s a question for you: what are you using to test your ideas?

SelectorGadget: point and click CSS selectors

SelectorGadget is an open source bookmarklet that makes CSS selector generation and discovery on complicated sites a breeze.

Ruby Kernel system, exec and %x

The Ruby Core Library documentation is very similar for Kernel.system, Kernel.exec and %x[..]. Recently I needed to kick off a system process, so I spent some time working with all 3 options.

Node.js is genuinely exciting

I don’t see myself switching all of my server-side development over to JavaScript, but Node has definitely earned a place in my toolbox. It shouldn’t be at all hard to mix Node in to an existing server-side environment—either by running both behind a single HTTP proxy (being event-based itself, nginx would be an obvious fit) or by putting Node applications on a separate subdomain. Node is a tempting option for anything involving comet, file uploads or even just mashing together potentially slow loading web APIs. Expect to hear a lot more about it in the future.

dcparker's ruby-gmail

A Rubyesque interface to Gmail. Connect to Gmail via IMAP and manipulate emails and labels. Send email with your Gmail account via SMTP. Includes full support for parsing and generating MIME messages.

Version 1 Sucks, But Ship It Anyway

There's no question that, for whatever time budget you have, you will end up with better software by releasing as early as practically possible, and then spending the rest of your time iterating rapidly based on real world feedback.

New Amazon EC2 Feature: Boot from Elastic Block Store

You can now launch Amazon EC2 instances from an AMI backed by Amazon EBS (Elastic Block Store). This new functionality enables you to launch an instance with an Amazon EBS volume that serves as the root device.

The Stars Look Down

...much as you and I may enjoy being encouraged through recognition and praise and dislike being saddened by rejection or indifference... deriving personal value from these transactions... is just plain faulty thinking, of the sort that makes otherwise capable, centred people all loopy and weird.

Questions for Jeffrey P. Bezos

For every 100 copies of a physical book we sell, where we have the Kindle edition, we will sell 48 copies of the Kindle edition. It won’t be too long before we’re selling more electronic books than we are physical books. It’s astonishing.

Campfire API

The Streaming API allows you to monitor a room in real time.

Mounted Web Apps Sites

...and between the two of use we had a Pancake stack that was proxying to couchdb in pretty short order.

Converting Rails application data from MySQL to PostgreSQL

Our antiquely Perl-like script worked better than we expected — our application started right up with all of its data intact.

State of Ruby VMs: Ruby Renaissance

In a short span of just a couple of years, the Ruby VM space has evolved to more than just a handful of choices: MRI, JRuby, IronRuby, MacRuby, Rubinius, MagLev, REE and BlueRuby. In fact, keeping up with all of the most recent developments within each VM is now easily a full-time job. For that reason, and with RubyConf ‘09 in full swing, let’s take a quick survey of the space and where it’s taking us.

Odeo Releases Twttr

There is also a privacy issue with Twttr. Every user has a public page that shows all of their messages. Messages from that person’s extended network are also public. I imagine most users are not going to want to have all of their Twttr messages published on a public website.

Why I Don't Care That I'm Killing Music

...and brought to their knees they should be, without a doubt. For years they have enjoyed a monopoly, where they controlled the price of music and kept it artifically high to fuck us over. Personally, I don't think I would feel so good about stealing shit from people if they hadn't spent the last 4 decades rubbing our noses in it...

Internet Vices

[Double True.]

Three things about Marco Arment

All of this happens with zero intervention from me. Which means substantial, challenging prose that used to get skipped in the rush of the day now becomes available anyplace it suits me. In the line at the ATM. On a plane. Wherever.

Airfoil Speakers Touch 1.0.1 Finally Ships

The chorus of disenchanted developers is growing and we’re adding our voices as well. Rogue Amoeba no longer has any plans for additional iPhone applications, and updates to our existing iPhone applications will likely be rare. The iPhone platform had great promise, but that promise is not enough, so we’re focusing on the Mac.

Log in or sign up? - Leah Culver's Blog

...we have just added the concept of user accounts. This includes the need for registration and log in (as well as log out and forgot password and so on). Leafy Chat only requires an email address and a password for both registration and log in, so it would be great to have some clever way to have both forms on the homepage.

The Nerd Handbook

A nerd needs a project because a nerd builds stuff. All the time. Those lulls in the conversation over dinner? That’s the nerd working on his project in his head.

Hacker News: Help: I'm lost

From the outside you'd be amazed to know that inside I am in terrible turmoil. You know me because of code I've written, books I've published, and my contributions here. Perhaps you follow me on Twitter. But I have reached a point in my life where I do not know what to do, or where to turn.

Using the New Gem Bundler Today

As you might have heard, Carl and I released a new project that allows you to bundle your gems (both pure-ruby and native) with your application.

Using the Rubygems Bundler for Your App

The new Rubygems bundler makes managing your application’s gem dependencies easy. And for applications with many components, it makes separating components’ dependencies easy too.

Caching Tutorial for Web Authors and Webmasters

A Web cache sits between one or more Web servers (also known as origin servers) and a client or many clients, and watches requests come by, saving copies of the responses — like HTML pages, images and files (collectively known as representations) — for itself. Then, if there is another request for the same URL, it can use the response that it has, instead of asking the origin server for it again.

Interview with Ezra Zygmuntowicz – Engine Yard

The cloud providers are splitting into a few camps. On one side, you have companies like Amazon that offer infrastructure as a service (IaaS), and Google who offers platform as a service (PaaS). PaaS offers rapid development, and no server administration, but it locks you into a specific provider. Enter Engine Yard, a company that's enhancing Ruby on Rails to run on on top of arbitrary IaaS. In this interview Ezra Zygmuntowicz paints the picture.

CouchDB Twitter Clone Architecture

So I've been thinking through the architecture of a Twitter-esque system in Couch as a kind of thought exercise to get a better handle on some of the more difficult corners of view generation. What would be the most effective manner of creating Twitter-like status streams?

Understanding Access Credentials for AWS/EC2

Amazon Web Services (AWS) has a dizzying proliferation of credentials, keys, ids, usernames, certificates, passwords, and codes which are used to access and control various account and service features and functionality. I have never met an AWS user who, when they started, did not have trouble figuring out which ones to use when and where, much less why.

Multiple File Upload With Progress Bar Using jQuery

Today I am going to show you how to create a multiple file upload form that allows multiple file selection using Ctrl/Shift keys and also displays a progress bar for each of the selected files while they are uploading.

SWFUpload jQuery Plugin

When I first stumbled across SWFUpload about two years ago I was impressed by how easy it was to implement. However, their example code has always bugged me as being rather crap, having to assign a separate global event handler for each event, and the lack of multiple handlers for a single event.

Weekly Digest, 11-6-09

Posted by Weekly Digest in Weekly Digest on November 06, 2009

How to Gemify your Rails Plugins

Ever since Rails added support for declaring gem dependencies, there is really no (good) reason to use plain ol’ plugins.

Plugging Rack into Rails

Rails 2.3 has Rack baked in. It uses Rack for things like sessions and parameter parsing. But what if you want to add your own middleware to a Rails app?

The Meaning of Information Technology

The first commercial computer was the Lyons Electronic Office I and was used in 1951 to perform vast calculations pertaining to the making and consumption of biscuits. You see, after the war, J. Lyons & Co., a popular chain of British tea shops, was confronted with an appetite for pastries so astronomical (which is understandable given years of tedious disputes with Germany), that the human mind was incapable of solving unaided the problem of distributing tea cakes to their customers.

librelist.com

Librelist.com is a free as in freedom mailing list site for open source projects. It is a place for FOSS communities to discuss all the things they want without ads, censorship, signup requirements, bundled apps, or requirements that you use any particular email client or service.

Introducing Resque - GitHub

Resque is our Redis-backed library for creating background jobs, placing those jobs on multiple queues, and processing them later.

PersistentFS.com

PersistentFS is a fast and efficient POSIX-compliant file system that provides unlimited online storage in the Amazon Web Services (AWS) storage cloud. A PersistentFS file system can be mounted on any Linux computer connected to the internet and accessed like local storage. All data written to the file system is uploaded to Amazon S3 for reliable and cost effective off-site storage, while remaining instantly accessible. This allows you to take advantage of Amazon S3 using your existing software, without writing a single line of code.

CodeRack: Canonical Host

There are often times when you'll need to redirect requests for some domains or subdomains to a single canonical host. This middleware lets you specify the canonical host for your application, and will perform a 301 redirect for all non-canonical requests.

Rails Best Practices

[Nice overview.]

Why do we have an IMG element?

But none of this answers the original question: why do we have an element? Why not an element? Or an element? Why not a hyperlink with an include attribute, or some combination of rel values? Why an element? Quite simply, because Marc Andreessen shipped one, and shipping code wins.

gabriel's shrub

S3 Proxy for Google App Engine [Awesome.]

S3Hub: S3 Client (for Mac OS X)

View your S3 online storage, upload, download, set permissions, share with friends and more.

Official Google Blog: This week in search 10/30/09

On Wednesday, we rolled out our new music search feature, fully integrated into Google's web search. Now, when you search for a band, singer, song name, or album title, Google will recognize it and return a special music result on the top of the page. These new special music results do exactly what you want - they let you listen to the full song.

Traffic Server Podling Status Page - Apache Incubator

Traffic Server fills the need for a fast, extensible and scalable HTTP 1.1 proxy and cache. We have a production proven piece of software that can deliver HTTP traffic at high rates, and can scale well on modern SMP hardware. We have benchmarked Traffic Server to handle in excess of 35,000 RPS on a single box. Traffic Server has a rich feature set, implementing most of HTTP/1.1 to the RFC specifications.

Start-up studies: A pop quiz

There’s a classroom exercise that’s a part of the Stanford technology venture program hits its students with each year: If you had five dollars and two hours, what would you do to make as much money as possible?

One-handed computing with the iPhone

The easy single-handed operation of the iPhone1 is not one of its obvious selling points but is one of those little features that grows on you and becomes nearly indispensable. A portable networked computing and gaming device that can be easily operated with one hand can be used in a surprising variety of situations.

Netflix Everywhere: Sorry Cable, You're History

There are a million different ways for Netflix to fail. But that has always been the case. Netflix should have failed already, taken down by Blockbuster or Wal-Mart, kneecapped by Hollywood, made irrelevant by BitTorrent or iTunes. Yet time and again, the company has not only survived but quietly thrived—on the strength of its unique algorithms and its relentless focus on getting customers content they didn't even know they wanted.

Speaker's Tip: Don't tell the audience you aren't prepared

People take days off of work, spend hundreds on a conference ticket, travel for thousands of miles, and pay hefty rates for flights and hotels to come hear you speak, and you tell them you didn’t have time to prepare a talk? What’s cool about that?

Underscore.js

Underscore is a utility-belt library for JavaScript that provides a lot of the functional programming support that you would expect in Prototype.js (or Ruby), but without extending any of the built-in JavaScript objects.

The Y Combinator Startup School 2009 Summary

Y Combinator’s Startup School 2009 was an incredible learning experience for new and experienced entrepreneurs alike. There are ten talks. Here are their key points.

Module: Rack::Utils

Rack::Utils contains a grab-bag of useful methods for writing web applications adopted from all kinds of Ruby libraries.

Thoughts on the Whitehouse.gov switch to Drupal

Yesterday, the new media team at the White House announced via the Associated Press that whitehouse.gov is now running on Drupal, the open source content management system. That Drupal implementation is in turn running on a Red Hat Linux system with Apache, MySQL and the rest of the LAMP stack. Apache Solr is the new White House search engine. This move is obviously a big win for open source.

Things Caches Do

There are different kinds of HTTP caches that are useful for different kinds of things. I want to talk about gateway caches — or, “reverse proxy caches” — and consider their effects on modern, dynamic web application design.

WebSequenceDiagrams.com - Create sequence diagrams in seconds

Don't waste your afternoon drawing UML Sequence Diagrams. Just enter the description here, and click "draw". The SD/MSC Generator is an easy alternative to using mouse-centric tools like Microsoft Visio.

stefankroes's ancestry

Ancestry allows the records of a Ruby on Rails ActiveRecord model to be organised as a tree structure (or hierarchy). It uses a single, intuitively formatted database column, using a variation on the materialised path pattern. It exposes all the standard tree structure relations (ancestors, parent, root, children, siblings, descendants) and all of them can be fetched in a single sql query.

Treating User Myopia

When I said users don't read anything you put on the screen, I was lying. Users do read. But users will only read the absolute minimum amount of text on the screen necessary to complete their task. I can't quite explain it, but this kind of user myopia is epidemic. It's the same problem, everywhere I turn.

The Amazon Relational Database Service (RDS)

Today marks the launch of Amazon RDS - the Amazon Relational Database Service. Amazon RDS is a web service that makes it easy to set up, operate, and scale a relational database in the cloud. Amazon RDS handles all the "muck" of relational database management freeing up its users to focus on their applications and business.

Flickr! It’s made of people

We’ve launched People in Photos, a new feature that will help put a face to the Flickrverse and enable you to highlight members that you’ve photographed in a whole new way. People in Photos lets you add a member to a photo, find photos of people you know, and manage which photos you’re in.

How We Made GitHub Fast

Now that things have settled down from the move to Rackspace, I wanted to take some time to go over the architectural changes that we’ve made in order to bring you a speedier, more scalable GitHub.

Ruby Enterprise Edition Features Guide

With REE, one can tune the garbage collector’s behavior for better server performance. It is possible to specify the initial heap size to start with. The heap size will never drop below the initial size. By carefully selecting the initial heap size one can decrease startup time and increase throughput of server applications.

Passing environment variables to Ruby from Phusion Passenger

Some environment variables must be set before Ruby is started because the Ruby interpreter itself uses them. The RailsBench GC settings environment variables, which are now supported by Ruby Enterprise Edition, are examples of such environment variables.

Using the Nginx Memcached module with Passenger

Nginx, everyone's favorite speedy web server has a module to hook in directly to memcached. For those of us running Ruby servers behind nginx we can avoid hitting our running Ruby processes completely on a cache hit.

Surprises

Now, when coding, I try to think: “how can I write this such that if people saw my code, they’d be amazed at how little there is and how little it does”.

Railssummit Slides

Here are the slides of [Pratik Naik's] presentation at Railssummit 2009... about Rails focused tips/tricks.

Mint CEO Aaron Patzer on Startups

Mint CEO Aaron Patzer talks with entrepreneurs at a JuicePitcher event about the history of his startup, Mint.

Connecting to Multiple Databases Using ActiveRecord

You can call establish_connection with the key that points to another database config in your config/database.yml file

Shortwave

...is an extensible quick-search and shortcut bookmark. [Awesome.]

What problems does Google Wave solve?

It will probably take years before Wave fully penetrates large corporations and replaces the email systems everyone is used to. But it solves so many thorny problems with email that it might well manage to do so, where so many other tentative “email fixes” have failed.

21 Rack Middlewares To Turbocharge Your Ruby Webapps

In this post, we're going to highlight various Rack middlewares from CodeRack, an on-going Rack middleware competition...

hiddenloop's paging_keys_js

Keyboard short cuts for paging through listings one item at at time (and across entire pages). Inspired by the navigation at FFFFOUND!

no-www Rack Middleware

Posted by Trevor in General on November 05, 2009

I'm pleased to present my submission to the CodeRack contest: no-www.

This middleware catches requests that begin with “www” and redirects them to the more reasonable "non-www" address.

For example: http://www.example.com -> http://example.com

While such redirects might better be performed from within an Apache or nginx config, some hosts (i.e. Heroku) don't give you access to configure the server as such.

If you're unfamiliar with the no-www movement, the philosophy is simple. Websites should have a canonical address. This address shouldn’t begin with “www” because the use of "www" is unnecessary and wasteful. See http://no-www.org/ for details.

And, without further ado:

If you know what Rack is, you problably already know how to use this. Still, an example usage for a Rails app wouldn't hurt. Start by copying the above middleware into lib/no_www.rb. Then, configure your application to use the middleware by placing the following in config/environment.rb:

 
Rails::Initializer.run do |config|
  config.middleware.use “NoWWW” if RAILS_ENV == ‘production’
end

No more www.

Installing Varnish with nginx, Passenger, and Monit on Ubuntu 8.10 intrepid

Posted by Trevor in Ruby/Rails on October 22, 2009

Varnish is a state-of-the-art, high-performance HTTP accelerator. I first came to know about it thanks to Heroku, where they use it to provide built-in HTTP Caching.

As their docs describe, using Varnish is easy:

# This tells the cache (Varnish) to serve the page for 300 seconds (5 minutes).
 
class MyController < ApplicationController
  def index
    response.headers['Cache-Control'] = 'public, max-age=300'
    render :text => "Rendered at #{Time.now}"
  end
end

Simply setting the "Cache-Control" header like so allows you to serve up a page extremely quickly because requests completely bypass your application logic, database, and all of that related overhead and read straight from the cache.

If you're serving up the same page to all visitors, then setting up Varnish HTTP caching is a no-brainer. If you're serving up pages that are mostly the same for all users but have a custom header or something, you can still take advantage of the caching speed boost if you're willing to investigate the ins and outs of ESI and/or serving partials with Javascript. If you're serving pages that are different for each user, then you're out of luck :)

So, using Varnish for HTTP acceleration is great, but unfortunately for me the version of Ubuntu (8.10 intrepid) that we're using has a painfully out of date package in aptitude. If you're already running Varnish, you can check to make sure you're using a relatively recent release by running varnishd -V. If you see anything less than 2.0.4, you should seriously consider upgrading.

Thanks to the helpful people on the Varnish mailing lists, I was able to get things up and running by doing the following:

Note that there’s a new version of Varnish out now. The 2.0.4 tag is still pretty good, but you should check all the available tags and decide if you’d rather use a newer version. If so, you’ll have to adjust the installation instructions found at the top of this post slightly.

Note that the .deb files generated by the “dpkg-buildpackage” command may be different from those generated at the time this post was written. The basic steps still apply, though.

apt-get update
apt-get install subversion autotools-dev automake1.9 libtool autoconf libncurses-dev xsltproc quilt
cd /tmp
svn co http://varnish.projects.linpro.no/svn/tags/varnish-2.0.4
cd varnish-2.0.4/varnish-cache
dpkg-buildpackage
cd ..
dpkg -i libvarnish1_2.0.4-6_i386.deb
dpkg -i varnish_2.0.4-6_i386.deb

You can then use /etc/init.d/varnish to stop/start/restart the service.

But, we're not done yet. Since it took me a while to get the whole app server stack configured, I thought it might help someone else out if I covered the rest of the steps it took to get Varnish working properly with my Ruby application.

You can get nginx installed with Ruby Enterprise Edition and Passenger by following the excellent documentation on the Phusion website.

I might suggest, however, doing the installation like this in order to get the latest (secure) version of nginx. Even before that, you'll probably want to install Ruby Enterprise Edition, which I like to do the old fashioned way.

You may also be interested in this example nginx init.d config, which allows you to use nginx as you would if installed from a package. Make sure to consider doing some kind of log rotation with this kind of setup as well.

...

Now that you're using the fantastic nginx web server, you'll want to configure it to listen to port 8080, so that Varnish can listen to port 80 and forward any requests that aren't in its cache to the backend server (nginx). I'll just post the complete config we're using, and you can pick out the relevant details for your case.

Some interesting things to note is that this setup is configured to use Sinatra, the lightweight Ruby web framework. If the application throws an exception, we're routing to the /error page. We're also using various other settings that you may or may not agree with. The important part with regard to Varnish and nginx cooperating, however, is that you set nginx to listen to port 8080 in your config file. My config is located in /opt/nginx/conf/nginx.conf:

worker_processes 1;
pid /var/run/nginx.pid;

events {
  worker_connections  1024;
}

http {
  access_log /var/log/nginx_access.log;
  error_log /var/log/nginx_error.log;
  passenger_root /opt/ruby-enterprise/lib/ruby/gems/1.8/gems/passenger-2.2.5;
  passenger_ruby /opt/ruby-enterprise/bin/ruby;
  passenger_max_pool_size 10;
  include mime.types;
  default_type application/octet-stream;
  sendfile on;
  tcp_nopush on;
  keepalive_timeout 65;
  gzip on;
  gzip_comp_level 2;
  gzip_buffers 16 8k;
  gzip_disable "MSIE [1-6]\.";
  gzip_proxied any;
  gzip_types text/plain text/css application/json application/x-javascript text/xml application/xml application/xml+rss text/javascript;

  server {
    listen 8080; # the important part!
    root /var/www/example/current/public;
    passenger_enabled on;
    passenger_use_global_queue on;
    rack_env production; # use rails_env for a rails app
    # serve static files without running more rewrite tests
    if (-f $request_filename) {
      break;
    }
    # disable site via capistrano (cap deploy:web:disable)
    if (-f $document_root/system/maintenance.html) {
      rewrite ^(.*)$ /system/maintenance.html break;
    }
    # expires headers
    location ~* \.(ico|css|js|gif|jp?g|png)(\?[0-9]+)?$ {
      expires max;
      break;
    }
  }
}

Now, I'm fairly new to using Varnish, so perhaps someone can advise me about how to better configure things, but I'll cover how I did it. Varnish comes with a few example configs loaded up in /etc/default/varnish. I ended up using the following:

NFILES=131072
MEMLOCK=82000
INSTANCE=$(uname -n)
DAEMON_OPTS="-a :80 -f /etc/varnish/default.vcl -s file,/var/lib/varnish/$INSTANCE/varnish_storage.bin,1G"

You can review the examples provided and see how you want to go about it, though.

Once you're all set with the general config, you'll need to provide a VCL config. I'm putting ours in /etc/varnish/default.vcl and it looks like this:

backend default {
  .host = "127.0.0.1";
  .port = "8080";
}

# Warning: read the following before using this config:
# http://varnish.projects.linpro.no/wiki/VCLExampleCacheCookies

sub vcl_recv {
  unset req.http.cookie;
}

The first part tells Varnish to forward any requests that aren't in its cache to a webserver running on localhost port 8080. That's nginx!

The second part unsets any cookies that are sent along with any requests. You won't want to do this unless you're serving the same pages for all users for your entire application. If you aren't careful here, you can very easily end up serving pages meant for one user to another. Be careful!

In my case this works fine because we're serving a site with no user-specific actions or views. It's all public. You're case might be different. Perhaps you can cache things like static files (images, etc) or certain areas of your application. Maybe you have a CMS with an admin interface that can't be cached, but with publically viewable pages that could be cached. I dunno. In any case, you should definitely read more about this on the Varnish wiki.

Finally, since we're using Monit to monitor the health of our systems, I'll throw in an example config that covers SSH, nginx, and Varnish. This Monit config would email you using a Google Apps Domain if there was a problem. You probably wouldn't want to use this as-is, but it should serve as a decent starting point for you to create your own. We've got the config in /etc/monit/monitrc:

# Alerts
set daemon 120
set logfile syslog facility log_daemon
set mailserver smtp.gmail.com port 587
    username "noreply@example.com" password "sldkjkfdsj"
    using tlsv1
    with timeout 30 seconds
set alert tech@example.com with reminder on 30 cycles
set httpd port 2812
allow example:slkdjlskdjflskjd

# SSH
check process sshd with pidfile /var/run/sshd.pid
start program "/etc/init.d/ssh start"
stop program "/etc/init.d/ssh stop"
if failed port 22 protocol ssh then restarts
if 5 restarts within 5 cycles then timeout

# nginx
check process nginx with pidfile /var/run/nginx.pid
start program = "/etc/init.d/nginx start"
stop  program = "/etc/init.d/nginx stop"
if failed host 127.0.0.1 port 8080 then restart
if cpu is greater than 40% for 2 cycles then alert
if cpu > 60% for 5 cycles then restart
if 10 restarts within 10 cycles then timeout

# Varnish
check process varnish with pidfile /var/run/varnishd.pid
start program = "/etc/init.d/varnish start"
stop  program = "/etc/init.d/varnish stop"
if failed host 127.0.0.1 port 80 then restart
if cpu is greater than 40% for 2 cycles then alert
if cpu > 60% for 5 cycles then restart
if 10 restarts within 10 cycles then timeout

That's all folks!

Weekly Digest, 10-12-09

Posted by Weekly Digest in Weekly Digest on October 12, 2009

Monthly Digest? ;)

Pomodoro

Pomodoro Desktop is a desktop application for Time Management on your Mac OSX. It is a simple but effective way to manage your (coding) time, and it's based on the Pomodoro technique

Clean CSS

Optmize and Format your CSS

Hacker News | GitHub's Unicorn Setup

[Interesting comments as usual.]

Picnik

Photo editing the easy way, online in your browser. Picnik makes your photos fabulous with easy to use yet powerful editing tools. Tweak to your heart’s content, then get creative with oodles of effects, fonts, shapes, and frames.

Unicorn! - GitHub

We’ve been running Unicorn for more than a month. Time to talk about it.

Munin

Munin the monitoring tool surveys all your computers and remembers what it saw. It presents all the information in graphs through a web interface. Its emphasis is on plug and play capabilities. After completing a installation a high number of monitoring plugins will be playing with no more effort.

On Gem Forking

So, GitHub has recommended Gemcutter as an alternative to hosting gems on GitHub...

Cloudvox

API-driven phone calls, in minutes (call your code: AGI/AMI, HTTP, Asterisk-Java, Adhearsion). Cloudvox is the most practical, stable, open environment for API-driven phone calls.

Gem Building is Defunct

We will continue to serve old gems at http://gems.github.com/ for at least one year. [New gems can't be built, though.]

* is Unix

Ryan’s I like Unicorn because it’s Unix appears to have started a mini-meme of folks writing simple forking network servers in their language of choice. I’m really enjoying reading ‘em — they’re a sort of Rosetta Stone of network code...

Chargify

Chargify simplifies recurring billing for Web 2.0 and SaaS companies.

Everything I know about Open Source I learned from Indie Hip Hop

Slides from an Aloha on Rails presentation.

FlipClock

Get the FlipClock Widget for your Dashboard!

nginx and varnish on Mac OS X

Since I'm a happy user of the macports collection already anyway, I let it do the 'heavy lifting' of actually installing nginx and varnish. In addition I provided a launchd startup item for varnish and also added a host entry for wahlcomputer to enable virtual hosting for nginx and varnish.

atmos's rack_hoptoad

A gem that provides exception notifications to hoptoad as rack middleware.

Ubuntu Intrepid - adding an Nginx init script

...let's go ahead and create one for easy control of Nginx, and to ensure it restarts on a reboot.

Generate gem.yml and .gems for Rails

A rake task which will generate gem configuration files based on your “config.gem” specifications in Rails. This comes in handy when deploying to Engine Yard, or Heroku.

Custom Chef Recipes with Engine Yard Cloud

One of the power user features of Engine Yard Cloud is the ability to use custom Chef recipes to install or configure anything that can run on Gentoo Linux that we have not already automated as part of the platform. This allows for extensive customizations of your environments and empowers you to run virtually all custom software you might need.

SHJS

SHJS is a JavaScript program which highlights source code passages in HTML documents. Documents using SHJS are highlighted on the client side by the web browser.

Getting ready for CouchDB 0.10

I’ve setup a local copy of CouchDB, from the 0.10 branch, just to see if my application code could handle its awesome powers. Here are my two big takeaways...

Paperclip, S3 & Delayed Job in Rails

Here’s how I use Paperclip (with storage on S3) and delayed_job to process images after they’re uploaded in the background.

Ryan Singer of 37signals - UI Fundamentals for Programmers

I gave a talk on “UI Fundamentals for Programmers” at WindyCityRails in Chicago last month. The talks covered modeling, breaking apps into screens, visual techniques, flows, and a few coding tips. [This is a great talk. Highly recommended viewing.]

Source code beautifier / syntax highlighter – convert code snippets to HTML

hilite.me converts your code snippets into pretty-printed HTML format, easily embeddable into blog posts and websites.

Keeping controllers empty with faux attributes - Momoro Machine

The barely any code way... use a fake attribute. Define an attribute setter on User, and then just make a small form in the view to set it.

Build it

The good innovation -- the innovation that makes the world a better place and builds real wealth in society -- that stuff is done by radically self-reliant creators who get their hands dirty. Not talkers. Not dreamers. Builders.

ActionRails

At ActionRails, we offer a variety of services designed to push your Rails developers to the next level... Application Evaluation; Weekly Code Reviews; Developer Hotline.

And if only 1% of those people...

...he forgot there was a number lower than one percent...

Working hard is overrated

Much more important than working hard is knowing how to find the right thing to work on.

Nginx_As_a_Reverse_Proxy - Couchdb Wiki

Nginx can serve as a reverse proxy to CouchDB for scenarios such as URL rewriting, load-balancing, access restriction, etc.

S3Sync

This is a ruby program that easily transfers directories between a local
directory and an S3 bucket:prefix. It behaves somewhat, but not precisely, like the rsync program. [I can verify that this is an awesome little tool.]

Full Stack ETag Support

The conclusion that I draw is that I definitely want to use Rack::Cache—100% improvement over reassembling the HTML on each request is too good to pass up. As for the 20% speed boost that full stack ETag buys me, I am not sure that the complexity that is introduced warrants the speed boost.

Browser Cache Usage Exposed

...reducing the number of HTTP requests has the biggest impact on reducing response time...

Place Pages for Google Maps

A Place Page is a webpage for every place in the world, organizing all the relevant information about it. By every place, we really mean *every* place — there are Place Pages for businesses, points of interest, transit stations, neighborhoods, landmarks and cities all over the world.

couchapp

CouchApp is designed to structure standalone CouchDB application development for maximum application portability. CouchApp is a set of scripts and a jQuery plugin designed to bring clarity and order to the freedom of CouchDB's document-based approach.

nginx, worker_processes, and passenger_max_pool_size

The Phusion Passenger pool size is independent from the number of
Nginx worker processes that you have. Setting the number of Nginx workers to the number of CPU cores should be sufficient.

Sinatra: Writing Extensions

Sinatra includes an API for extension authors to help ensure that consistent behavior is provided for application developers.

How Should Mac Apps Be Distributed?

...but to make this work for apps delivered by disk image, users have to understand that they must copy the app from the image to their startup drive. This is where some get lost.

Sammy.js, CouchDB, and the new web architecture

Welcome to the new world. HTTP Databases and JSON Storage. The simple act of making the database and the browser more powerful on either end has destroyed the need for the middle tier.

GitHub is Moving to Rackspace!

In just a few short weeks we will be moving GitHub to a new home at Rackspace. We’re aware of the current stability and performance issues, and we want to let you know what we’re doing about it.

hurl

Hurl makes HTTP requests. Enter a URL, set some headers, then view the response. Perfect for APIs.

Pygments

Posted by Trevor in General on September 16, 2009

I'm pleased to announce the immediate availability of http://pygments.appspot.com. It's an unofficial API for the Pygments syntax highlighting library. It's designed to provide syntax highlighting for web applications that don't have Python installed. You can think of it as an HTTP interface for Pygments.

To use it, simply POST to http://pygments.appspot.com with "lang" and "code" parameters in the body. You'll receive pygmentized HTML back, which you can store for later display on your site.

I'm using it so that I can host Flowcoder on Heroku. I was really impressed with the ease of getting this Pygments app running on Google App Engine. GAE is very much like a Python version of Heroku, which means it's awesome.

I'm hoping that this little project will spike my interest in learning a bit more about Python, which actually doesn't seem as evil as all my Ruby friends have made it out to be :P

The source code is on github, in case you're curious about how this all works.

Enjoy!

http://pygments.appspot.com

Passenger with nginx on Mac OS X

Posted by Trevor in Ruby/Rails on September 16, 2009

Setting up nginx with Passenger support turns out to be fairly easy.

Start by making sure you have the most recent version of Passenger, then install the nginx module. This will actually install and compile nginx with the Passenger module enabled, which is handy. Choose the recommended/default options when the installer prompts you.

sudo gem update passenger
sudo passenger-install-nginx-module

Then, open up the nginx config file:

mate /opt/nginx/conf/nginx.conf

Add the following line to the top of the file:

daemon off;

This will prevent the "502 Bad Gateway" error you may see otherwise. I'm not sure why this is necessary, but I read about it here, and it seems to do the trick. nginx specifies that this should only be used for development, though.

Next, find the http { block, which should start around line 15 or so. You'll want to add a server { block within the http { block for each of your Rails/Rack applications, like so:

server {
   listen 80;
   server_name eldorado.local;
   root /Users/trevorturk/Code/eldorado/public;
   passenger_enabled on;
   rails_env development;
}

You'll need an entry in your hosts file if you don't already have one. Simply open up the file:

mate /etc/hosts

...and add lines for each of the apps you plan to run, like so:

127.0.0.1 eldorado.local 

Now, we can set up a launchd item, so that nginx will start up automatically after a system reboot. Create a new plist file by opening it up in TextMate:

mate /System/Library/LaunchDaemons/nginx.plist

...and paste the following code in, which was kindly provided for us by this helpful person:

Then, run the following command to load it:

launchctl load -F /System/Library/LaunchDaemons/nginx.plist

Now, you can reboot your system and make sure it's all working as expected by visiting http://eldorado.local, or whatever address you've configured your application to be on.

I believe this nginx installation will override the existing Apache installation you may have running. This doesn't bother me, so I opened up my System Preferences -> Sharing prefpane and unchecked the Web Sharing box, so Apache is no longer running. If you have any ideas about how to keep both services running cooperatively, please do let me know.

Update: Here are some additionally configuration options I'm using, which I cobbled together from various sources after Googling for things like "nginx, rails, gzip, expires" and such. Their powers combined, and I seem to have a YSlow-approved setup.

Just above your server { block, around line 40, add the following:

gzip on;
gzip_buffers 16 8k;
gzip_disable "MSIE [1-6]\.";
gzip_proxied any;
gzip_types text/plain text/css application/json application/x-javascript text/xml application/xml application/xml+rss text/javascript;

That should cover gzip well enough.

Then, amend the aforementioned server { block to include some far future expires goodness that takes advantage of the Rails asset_tag helpers:

server {
  listen 80;
  server_name eldorado.local;
  root /Users/trevorturk/Code/eldorado/public;
  passenger_enabled on;
  rails_env development;
  location ~* \.(ico|css|js|gif|jp?g|png)(\?[0-9]+)?$ {
      expires max;
      break;
  }
}

These two configuartion tweeks are, I believe, the rough equivalent of the technique previously discussed on this blog for Apache.

Of course, any additional suggestions, comments, or insights you may have would be most welcome. I'm new to this whole nginx thing, but I'm enjoying it so far.

Update: Here's an easy way to reload nginx, if you need to make a change to your conf. Make sure to have the following in your /opt/nginx/conf/nginx.conf file:

pid /var/run/nginx.pid;

Then, you can make an alias for the reload task in your ~/.bash_profile:

alias nr='sudo kill -HUP `cat /var/run/nginx.pid`'

In case you're interested, you can check out my full nginx.conf file for local development here:

http://gist.github.com/191331

Static: a super simple Rails CMS for Heroku

Posted by Trevor in Ruby/Rails on September 11, 2009

Static is a super simple Rails CMS built for Heroku. It supports file uploads to S3, makes image thumbnails, lets you make pages, has an optional admin password, and a customizable application layout that supports erb. It's really easy to install and deploy to Heroku. If you have an S3 account, you can get up and running in under 5 minutes.

I made this little app a few weekends back because it scratched a personal itch of mine. I maintain a few small "static" or "brochure" sites for friends, which means I get to do boring HTML updates whenever they have a new picture or video they want to add. I figured that I could do a little upfront work and let them to do the rest. So, I looked around for a simple Rails CMS, but I couldn't find anything simple enough. Thusly, Static was born.

It doesn't do much for you, but that's the point. You get a really simple little Rails app that lets you add pages, upload stuff, and wrap everything in a layout that can be updated online. If you ever need to add any cool new functionality (like displaying recent Twitter updates?) you can do it using Ruby/Rails. No more lame old hacked-together PHP sites ;) Static's well-tested, 175 line code base could be the solid foundation for a site that grows over time.

This thing does exactly and only what I need it to do, but I'm happy to accept patches and such. Give it a shot, fork away, and let me know if you have something good for me to pull.

http://github.com/trevorturk/static/

Enjoy!

Weekly Digest, 9-11-09

Posted by Weekly Digest in Weekly Digest on September 11, 2009

Still not weekly ;)

Github and Engineyard part ways

[This Hacker News thread has some more detail from EY and GH. EY couldn't afford to continue with the preexisting arrangement, so GH is moving to Rackspace.]

Tornado Web Server

Tornado is an open source version of the scalable, non-blocking web server and tools that power FriendFeed. The FriendFeed application is written using a web framework that looks a bit like web.py or Google's webapp, but with additional tools and optimizations to take advantage of the underlying non-blocking infrastructure.

Twitter And The Revenue Dilemma

The company has to decide whether or not to turn revenue on. It sounds ridiculous, but it is a real decision. Once revenue is on, how the company is valued by the market can change dramatically.

Using Ruby Enterprise for Rails script/console

If you want to just use REE for script/console, without setting it for
everything, you can...

If architects had to work like software developers

Please don’t bother me with small details right now. Your job is to develop the overall plans for the house: get the big picture. At this time, for example, it is not appropriate to be choosing the color of the carpet. However, keep in mind that my wife likes blue.

Ravelry

What we’ve done only takes 1 not-even-fulltime (I have lots of other duties) programmer/sysadmin and it’s very cool that the software available today makes this possible. It’s important — we can’t be spending money on “professional services” and we only have 3.5 employees.

How Twitter works in theory

It is said that an economist is someone who sees something that works in practice and wonders whether it works in theory. Twitter clearly works in practice... and I wanted to write about some theories that help me understand it.

MiniBatteryStatus Widget

MiniBatteryStatus is a small Dashboard widget that monitors battery status, charge percentage and remaining battery life. Integrated with Growl to alert you when it's time to recharge your battery.

Protecting your Paperclip downloads

[Excellent write-up that covers protected downloads using Apache, nginx, the local filsystem, and/or Amazon S3. Awesome.]

Yehuda Katz Interview

A pretty good idea would be to contribute heavily to open source, and then look for work at companies that look at open source work as equivalent to a resume. If you build up enough really good open source work, you'll soon find people clamoring to hire you. [Even with my limited experience, I've found this to be true. Working in Open Source is a really efficient way to improve your skills, and helps immensely when looking for work.]

Mac OS X 10.6 Snow Leopard: the Ars Technica review - Ars Technica

Mac OS X 10.6, aka Snow Leopard has landed. This time around, Apple goes light on the glitz in favor of some heavy work under the hood. John Siracusa dives deep into Apple's new OS offering to see what's new, what's still the same, and whether it's worth upgrading.

aM laboratory

Simple sinewave synthesizer triggered by an ordinary 16step sequencer. Each triggered step causes a force on the underlaying wave-map, which makes it more cute.

Poor Man’s Heroku Backups

Posted by Trevor in Code, Ruby/Rails on September 11, 2009

Here's a quick and dirty way to back up all of your Heroku-powered databases using their Taps gem with one easy command. It works well enough for my simple needs, but any improvements you've got would be most welcome!

Just add the following to your ~/.bash_profile, and you're good to go: