December 20, 2010
Have you spent any time playing around with Mirah yet? You should. It’s developing into a pretty awesome language. Or maybe just a fantastic Ruby-like syntax for Java, depending on how you look at it. Mirah as a language (err, compiler) is still a work in progress, but it’s very usable as-is and fun to play around with.
If nothing else, it certainly makes writing trivial Android applications more enjoyable. Want to write one yourself? Check out Protoform, a little Mirah Android app generator that I tossed together a few weeks ago. Install it via Rubygems and get your droid on:
gem install protoform
protoform -S ~/android/sdk -T "Hello Android" -P org.zerosum.android HelloWorld
You’ll want to have JRuby and Mirah installed of course. Get JRuby with RVM and then gem install Mirah.
If you want to do Android work in straight Ruby instead, you can take a look
at Ruboto. However, Ruboto runs on Android
via JRuby, which means the runtime needs to be bundled in to the APK, leading
to large file sizes and slow execution. Mirah, on the other hand, compiles
straight to Java bytecode with no middleman and makes direct use of the Google
Android APIs. Ruboto is under heavy development and coming along nicely though, and the more Ruby-like API wrappers are a welcome alternative.
Both of these projects have the potential to be pretty important stuff. As
does anything else that makes mobile client development less painful
(Appcelerator, Phonegap, Rhomobile, etc).
November 01, 2010
Manually deploying static site updates is so 2003. And Capistrano is great, but it’s an extra step you don’t always need (and somewhat overcomplicated). If you’re using Jekyll to power your site and already have your data in Git, it’s pretty easy to set up a pure Git deployment workflow. Even if you’re not using Heroku ;-).
By using either Gitosis or (better yet) Gitolite, you can be autodeploying like a boss in just a few minutes. And, because Gitolite allows you to manage repository access across ad-hoc groups, you can easily allow other users to push to your remotes and update the appropriate sites without them needing shell access on your server. And share those users across multiple projects, and so on and so on.
Here’s how I set up the deploy recipe that I use for updating this blog and a couple other static sites that I’m hosting on the same box.
First, install Gitolite on the host you want to deploy to. Sitaram’s installation instructions are really easy to follow, but I’ll summarize here (I used the root method, which I suspect is what most readers would want to use too):
git clone git://github.com/sitaramc/gitolite gitolite-source
git checkout v1.5.6 (or whatever tagged version you want)
mkdir -p /usr/local/share/gitolite/conf /usr/local/share/gitolite/hooks
src/gl-system-install /usr/local/bin /usr/local/share/gitolite/conf /usr/local/share/gitolite/hooks
You’ll need to add a
git user, who will own the repositories on the system. Create one now, and finish the Gitolite installation process:
su - git
Make sure that you gave
gl-setup the correct public key from your local (client) system. Now, on your client, you should now be able to check out the gitolite admin repository, through which you can manage users, groups, and repository access.
git clone git@my-server:gitolite-admin
gitolite-admin/conf/gitolite.conf. Gitolite comes with a couple pre-defined group definitions (including one for the admin repository; don’t screw that one up). Adding a user permissions for a new repository goes like this:
RW+ = kyle stan
blog is the name of the repository you want to create, and
stan are two users who will need to be able to read and write to that repository. We have no way to identify Stan and Kyle yet, but that’s the next step. We’ll add their public keys to the
gitolite-admin/keydir directory. Make sure to name them
Add the new files to the git repo (
git add .) and commit everything. Push it to the remote with
git push origin master. This should push the gitolite admin changes back to your remote server and update the internal configuration, allowing Stan and Kyle to work on the blog project.
Managing a Static Site
For simplicity’s sake, let’s say that you’re Stan (Stan’s public key is your public key). To create the new repository and register it with Gitolite, you should now be able to do the following:
git add .
git commit -a
git remote add origin git@my-server:blog
git push origin master
Instead of just creating an empty index file, make it a simple html file, or drop in a basic Jekyll site. Or, instead of creating a brand new repository, just add a remote (call it
production perhaps?) to an existing Jekyll repository that you’ve been working on. In any case, when you push those commits up, Gitolite should check that your public key is authorized to perform that operation, and (assuming that it is) create the new bare repository for you automatically. Because it’s cool like that.
If you have a problem with this step, check that (a) your public key is indeed mapped to a username that is authorized to RW that repository, and (b) that the name in your gitolite.conf matches the public key filename.
If that all appears to be working, your next step will be to create a virtual host entry in your Apache config on the server (or your web server of choice). Here’s a basic Apache vhost:
CustomLog /var/log/apache2/blog-access.log combined
And of course, create the docroot destination and make sure the
git user owns it and can write to it. Then you can enable the config and restart Apache (or nginx or whatever).
Auto-Update on Deploy
I’m going to assume that we’re working with Jekyll here. And you should be, because it’s awesome. But if you are using some other static site generator, you can customize it pretty easily. The basic idea is that you want a post-receive hook to fire whenever the server receives a new push, and you want to regenerate the site data and redeploy it for everyone to see. This makes creating a new blog post really easy, for example.
/home/git/repositories/blog.git/hooks and edit the
post-receive file. You may also need to
chmod ug+x it so it’ll execute properly. Here’s what goes inside:
git clone $GIT_REPO $TMP_GIT_CLONE
cd $TMP_GIT_CLONE && jekyll --no-auto $TMP_GIT_CLONE $PUBLIC_WWW
cd ~ && rm -rf $TMP_GIT_CLONE
find $PUBLIC_WWW -type f -print0 | xargs -0 chmod 666
find $PUBLIC_WWW -type d -print0 | xargs -0 chmod 777
Save that, and then commit a sample change from your client and push it to the remote. The server should fire the post-receive hook automatically when the push has finished, and regenerate the site, dumping the changes into your docroot directory for the world to see. In fact, you should even see the Jekyll generation output in the git push command output, which makes it extra easy to troubleshoot in case you’re having a problem.
And voila, git auto-deploy goodness.
What’s best about this is that it’s easy to authorize new users to update a group site or blog, and manage those users all through their public keys and a simple config file. This config also makes it easy to spin up new static sites on the same host; just copy a couple configs and you’re good to go (or even better, investigate dynamically configured mass virtual hosting).
If you’re self-hosting your blog with some custom blog package you should really give this type of setup a look. I like it because it’s simple to manage access, incredibly quick to deploy updates, and everything is naturally stored in Git and in plaintext, so you’ve always got full revision history and never have to worry about vendor lock-in or proprietary formats. Need comments? Use Disqus. Less moving parts is almost always better. Simple is good.
October 30, 2010
This blog has been running Mephisto since 2007 or thereabouts. And it seems like the Mephisto project has been dead for just about that long too (check that link if you don’t believe me). So that’s awesome. But such is life… and open source.
Anyway, I’ve been meaning to migrate my blog over to something else for quite some time. Switching is of course a pain in the butt so I’d been puting it off, but the decommissioning of the server host this blog used to run on was finally the shove that I needed. After evaluating a few blog engine and hosted service options, I decided to go with Jekyll . Why? Because it’s simple, static, and seems to be pretty fad-proof at this point. Also, it’s Halloween. So it’s thematic. I considered moving stuff to Tumblr or Posterous, but the import process proved to be an obstacle. And not Halloweeny at all. In the end, Jekyll was clearly the simplest and most malleable solution, and so here we are.
Moving wasn’t too too painful. I whipped up a few scripts to yank the data I needed out of Mephisto and then spent a few extra hours cleaning up some sloppiness and making sure all the permalinks still worked. I ported the NH Ruby blog and a few other small sites that were running on a Mephisto multi-site install at the same time. I really wanted a pure Git workflow for easy deployment, so I created some post-receive hooks that auto-deploy the latest changes when someone pushes to origin/production. And because a few other people needed to be able to post to the other sites, I figured I’d set up Gitolite, which makes managing access control for such things crazy easy.
The only thing that didn’t make the transition is old blog comments. I went with Disqus for the new site because I wanted to keep everything static and simple (avoiding lock-in to yet blog package that may or may not ever be updated again), and importing the Mephisto comments into Disqus was just too much of a pain to justify the time. Sorry about that.
Anyway, I’m pretty happy with the new setup. If you find anything that’s broken please let me know. Maybe if I get some free time over the next couple days I’ll document the Gitolite + Jekyll deployment config. I imagine that it’s not completely unlike a minimalist version of what the GitWrite guys had to do for their (awesome!) Rails Rumble entry this year. And yeah, I probably could have just used them too. Don’t know why I didn’t think of that earlier ;-).
October 21, 2010
This is the fourth year I’ve helped organize the Rails Rumble innovation competition and the entries this year are definitely the best I’ve seen yet. Our panel of experts have finished making their finalist selections and public voting just opened, so head on over and help us decide who gets to do a victory dance this weekend.
August 30, 2010
Last year we launched a little web service called rdoc.info for hosting public docs for Ruby libraries. It wasn’t a completely new idea, but there was nothing else out there at the time that was free and open source and worked on Github post-commit hooks, so I put something quick together in a day and started using it. A bunch of other people started using it too, which was great, and people started contributing patches, which was even more great (thanks in particular to Jeff Rafter and Brian Turnbull). It grew as more people and organizations like our friends at Thoughtbot started hosting their library docs on it.
Today it hosts docs for almost 3000 different Ruby projects. And today we’re killing it.
RubyDoc.info is Rdoc.info 2.0
Well, actually, it’s more like we’re replacing it. With something newer and better, of course. That newer, better thing is RubyDoc.info (source on Github), a project that originally started out as the yardoc.org doc server grew into a full-fledged rdoc.info replacement. Loren Segal (the author of YARD, easily the best Ruby documentation engine ever) and I have been working on merging the projects together for awhile now, and it’s finally cooked well enough that we’re ready to swap it over.
The new site addresses a number of outstanding issues / feature enhancements that people asked for on the old site, and it’s much more tied into the YARD ecosystem. Also, in addition to supporting GitHub post-commit hooks, it also hosts documentation for all published RubyGems. We like it, and we hope you do too.
If You’re Already Using Rdoc.info
If your docs are already up on rdoc.info, don’t worry. Your old URLs should still work, so no need to update them right away. Your post-commit hooks will still work too. If you have any problems at all, please open a ticket on the project’s Github repository and we’ll do our best to get you squared away. Thanks!
Better Docs == Better Code
Also, in case you’re not already familiar with YARD, now is a great time to learn about it and how it can help you improve documentation for your code. This new site deployment coincides with the release of the brand new YARD 0.6 and Loren’s awesome new Yardoc.org site, which has some great guides and other resources to get you up to speed fast.
July 28, 2010
I just released a new version of Resque Mailer (1.0.0), my asynchronous email delivery extension for Resque gem src. If you’re already using it with Rails 2.x, there really aren’t any changes you need to be aware of. Go about your business. However, thanks largely to the efforts of Marcin Kulik, the gem now works in Rails 3.x as well. Thanks Marcin!
So why go 1.0.0? Because it’s feature complete, used by a number of people in production, and has been stable without any significant feature additions or issues for quite some time. It’s still simple as hell, and I don’t see it getting more complicated any time soon. And now that it works on both Rails 2.x and 3.x, well, that sounds like a 1.0.0 to me.
May 28, 2010
In case you’re not reading the Mogo blog, I posted a tutorial over there yesterday about how we integrate Google Analytics with Rails using OAuth and Garb . It’s not a terribly arduous process, but if you haven’t done much work with OAuth it can be confusing, and there are a couple unique Googly things about it that might otherwise trip you up.
The post includes complete code for an OAuth-backed authorizations controller too, which should help you get up and running quickly. And fwiw, it should actually be applicable to all the Google Data APIs, not just Google Analytics. Just change the request token scope.
And yeah, I really need to get back to blogging on a semi-regular basis, too.
March 12, 2010
Already got plans for this weekend?
The second Rails Camp New England is this weekend, March 12th to the 14th, in West Greenwich Rhode Island. Hope to see some of you there! Ask me about my new startup (want an invite?) or help me fix some of the outstanding Rdoc.info bugs if you’re looking for something to do :).
The last camp in summer of 2009 was a great experience and I’ve been looking forward to a repeat. Thanks to Brian Cardarella for putting it together.
January 09, 2010
We’ve been making heavy use of Chris Wanstrath’s Resque library in my latest project. Resque is a Redis-based background job system that Chris built for GitHub. It’s easy to use, especially if you’re already leveraging Redis in other parts of your infrastructure, and also has a nice Sinatra front-end for monitoring job status.
Anyway, Resque jobs are just Ruby classes that respond to the special perform method. They’re placed on a queue — you can place different jobs on different queues — and later, a worker polls the queue, pops the jobs off and performs the task.
We have a number of different asynchronous jobs happening in Mogo, many of which are domain-specific. But one thing we’re doing that’s very common is using the background system to process mail delivery asynchronously. Because synchronous mail delivery is for jerks.
Outgoing mail in a Rails app is generally handled by ActionMailer, which expects you to implement message delivery types as class methods on an ActionMailer “model” (a butchering of the term). So a typical mailer might look like this:
class Notifications < ActionMailer::Base
def signup(user_id, sent_at = Time.now)
@user = User.find(user_id)
subject 'Welcome to Mogo'
from 'Mogoterra <firstname.lastname@example.org>'
Then, to send a signup message, you use the following method call from somewhere else in your codebase:
So this all works good but it’s synchronous. You’d like to be able to background these tasks and use Resque. But you don’t really want to mess around with the mailer implementation. Right? Me too.
So ResqueMailer does just that.
Following in the footsteps of DelayedJobMailer, ResqueMailer allows you to shift processing of your existing mailers to an async Resque worker without doing pretty much anything. Just install the gem in your Rails project (via Gemcutter) and then mix the
Resque::Mailer module into your mailer.
class Notifications < ActionMailer::Base
You’ll need to restart your Resque workers and make sure at least one of them is working on the special
mailer queue (or * for all queues). Now when you call
MyMailer.deliver_signup, the task will be placed on the mailer queue and processed by the first qualifying worker.
It’s always nice when a tiny amount of code makes a task transparent. Check out the project page on GitHub for more information.
November 22, 2009
Rdoc.info is now serving up fresh docs using YARD 0.4.0. Doesn’t that new template look nice?
If you’re a Ruby OSS developer and haven’t checked out YARD yet, you really should. It’s easily the best way to generate sexy documentation for your projects and Loren has done a really awesome job with the latest release. The experimental new live docs service (with php.net-style user comments) that he’s testing out is swanky too, and we hope to roll this stuff into Rdoc.info shortly.
In the meantime, you can enjoy the latest YARD features and an updated look and feel. Make sure to add a post-commit hook to your GitHub-hosted project and we’ll automatically rebuild docs whenever you push a new release to your remote. Docs for older versions are maintained as well, and accessible via the usual commit hash url [example].