Benjamin Curtis

Speculations on Web Development

Default a Postgres Column to the Current Date in a Rails Migration

| Comments

If you want to have a Postgres column (aside from created_at) that you want to be populated with the current date if no other date is specified, you may be tempted to create a migration like this:

add_column :invoices, :paid_on, :date, default: 'now()'

That will look like it works – you create a record, it gets populated with today’s date, and all is good. However, if you look at your schema, you will notice that new field has a default of today’s date instead of now(). Oops. :)

You might try to create the column with the recommendation from the Postgres documentation:

add_column :invoices, :paid_on, :date, default: 'CURRENT_DATE'

But that fails because Rails tries to quote that ‘CURRENT_DATE’ for you before it goes to Postgres, which blows up. Now what?

Here’s how to do what you want:

add_column :invoices, :paid_on, :date, default: { expr: "('now'::text)::date" }

This avoids the quoting problem (by using expr) and avoids the always-insert-migration-date’s-date problem (by using the default function of (‘now’::text)::date, which is effectively the same as CURRENT_DATE.

And now when you insert a record without specifying a value for that field, you get the date of the insertion, rather than the date of the field being created. :)

Searchlight and CanCan

| Comments

I’m currently working on a client project where site adminstrators use the same UI that site users do, so there are permissions checks in the views and controllers to ensure the current user has the right to do or see certain things. CanCan provides the access control, which takes care of most of the issues with a simple can? check or load_and_authorize_resource.

In one case I wanted to provide search on a list of items (the index action) to admins so they could search through all items in the database, but users should be able to only search on their own items. I’m using Searchlight (highly recommended) for search, which returns results as an ActiveRecord::Relation, so it’s easily chainable via CanCan, like so:

class InvoicesController < ApplicationController
  def index
    @search = InvoiceSearch.new(params[:search])
    @invoices = @search.results.accessible_by(current_ability, :index)
  end
end

Searchlight is also smart enough to return all results if there no search params provided, so this also works as a typical index action that lists all items the user can see. If you’re curious about the @search instance variable, that is used in the search form in the index view.

So, if you need search with access control, use Searchlight and CanCan… they are a great combo!

Installing Ruby 2.0

| Comments

I had a bit of an adventure this morning getting Ruby 2.0 installed on my mac with Mountain Lion, so I thought I’d share the tale with you in case it can help save you some time on doing the same. Up until now I’ve been developing my Rails apps with 1.9.3, but it was time to upgrade and experience all the new hotness of the latest Ruby. I had tried to install Ruby 2.0 before, but I had been stymied by an openssl error when building. Today was to day to get that sorted.

I’m using rbenv to manage the different Ruby versions on my machine, so the first step was to update ruby-build, which I have installed via homebrew, so that I could fetch and build the latest Ruby. Sadly, I had some weirdness with my homebrew installation that prevented me from getting the latest homebrew, which prevented me from getting the latest ruby-build, which prevented me from being able to install the latest Ruby (2.0.0-p247):

$ brew update
error: Your local changes to the following files would be overwritten by merge:
...

I was pretty sure I hadn’t changed anything in homebrew myself, and I found some guidance in the github issues list for homebrew that I should just blow away my local changes with a git reset, which didn’t initially work because apparently some permissions had changed in /usr/local:

$ cd /usr/local/Library
$ git reset --hard FETCH_HEAD
error: unable to unlink old 'README.md' (Permission denied)
error: unable to unlink old 'SUPPORTERS.md' (Permission denied)
fatal: Could not reset index file to revision 'FETCH_HEAD'.

$ sudo chown -R `whoami` /usr/local
$ git stash && git clean -d -f
$ brew update

Now I was in business. Next up I upgraded ruby-build, and since I had already installed openssl via homebrew previously, I could use that while compiling:

$ brew upgrade ruby-build
$ env CONFIGURE_OPTS='--with-openssl-dir=/usr/local/opt/openssl' rbenv install 2.0.0-p247

Boom! Ruby 2.0 was finally installed. But then I hit a snag while trying to install gems for one of my Rails projects:

$ bundle
Could not verify the SSL certificate for https://code.stripe.com/.
There is a chance you are experiencing a man-in-the-middle attack, but most likely your system doesn't have the CA certificates needed for verification. For information about
OpenSSL certificates, see bit.ly/ruby-ssl. To connect without using SSL, edit your Gemfile sources and change 'https' to 'http'.

That was an especially useful error message, since that link provided a tip on easily getting some updated ssl certificates:

$ brew install curl-ca-bundle

And that tells you to

$ export SSL_CERT_FILE=/usr/local/opt/curl-ca-bundle/share/ca-bundle.crt

And now everything works. Woohoo!

Proven: Customer Interviews Save You Time and Money

| Comments

I’m on my way home from MicroConf 2013, having learned a lot and having had a lot of fun. This was the third year Rob and Mike have put on the conference, and the third year that it has been an awesome experience. As with the previous years, the speakers and the attendees were bright, informative, friendly, motivated, and motivating. If you run a bootstrapped biz, or are thinking about running one, MicroConf is the place to be to really increase your motivation for and your knowledge about running your business.

As an aside, I’m looking forward to BaconBizConf at the end of this month for the same reasons – I have no doubt it will also be a great place to be for those who are interested in getting better at making money. :)

I could write several blog posts about terrific takeaways from this conference, but in this one I want to focus on the urging (especially by Hiten Shah and Mike Taber) to focus on customer development when starting and growing your business. This topic had a particular impact on me at this time because it’s been on my mind the last few weeks.

A couple of weeks ago I had the privilege of attending the Switch Workshop put on by the Rewired Group and hosted by Jason Fried of 37 Signals. That one-day workshop (which I also highly recommend) was entirely focused on how people make purchasing decisions, and how understanding that process can help you find the right customers and give them the value for which they are searching. Going through that workshop really got me in the mindset of putting myself in my customer’s shoes (and head), and letting that drive the decisions I make about my business. I had been interested in customer development before, but that workshop really sold me on just how effective it is to talk to customers about how and why they’ve made the decisions they have made.

I work with entrepreneurs quite a bit in my consulting business (in fact, I work almost exclusively with people who have an idea and are wondering how they can convert that idea into a business), and all too often I see a lack of diligent customer research cause time and money to be wasted, building a product or service that not enough people really want. That’s the bad news. But the good news is that this particular problem is actually easy to overcome! And, even better, it doesn’t have to take a lot of time or money! And, best of all, it’s even fun! That workshop, and the emphasis that Hiten and Mike placed on really understanding your customer, gave me the the information and motivation I needed to implement a process to solve this problem for my own business and help others who face this very common problem.

The super-simplified, fun-to-follow and obscenely-effective process can be broken down into two steps. First, follow Hiten’s advice, and start with a hypothesis, which I’ll paraphrase a bit:

We believe that (some type of customer / customer segment) has a problem (with something or doing something)

Once you fill in the blanks with a very specific description of what you think your ideal customer is and with a description of what the job they want done is, then you are ready to move on to step number two (and this is where it gets fun): talking to those customers. But here’s the trick: Don’t talk about you! Talk about them! Talk about who they are and what they do (thus making sure they really are your target customer, and/or helping you learn about who your target customer is). Then, talk about what they are doing today to solve the problem that you are thinking of addressing. Ask them how they came to the solution that they are using, or how they confronted the problem on which you are focused. If all goes well, you’ll end up talking very little about the product or service idea in your head, and instead you’ll end up hearing a lot about what they do and how they do it, which will give you such good insights that you’ll find yourself smiling as they are talking.

Of course this process isn’t limited to just new ideas, products, or services. You can use this same process when working on a new feature for your current product, or when trying to find out why what you are currently offering isn’t quite as successful as you’d like it to be.

Now, you might be wondering how I know this process is worthwhile and fun. It’s because I’ve done it myself, of course! :) And I can certainly attest that it works wonders. In fact, I got to practice the process while still at MicroConf, since some of the attendees are ideal customers for my Rails application monitoring service, Honeybadger. There’s a new feature I’ve been thinking about the past few weeks, and I wanted to make sure I was on the right track with it. I had a hypothesis that Rails developers would like a better way to do activity X than the way they are currently doing it. So I found a few Rails developers that I had already been talking to during the conference, and I asked them one question: When do you do activity X and why? From that one simple question, and a short conversation that followed it, I realized that I was indeed on to something with my planned feature. More importantly, what I heard from my customers let me know that my planned approach was actually a bit flawed. And better yet, I realized that the approach that would better solve the problem (as they saw the problem) would actually be easier for me to implement than my initial plan. I was thrilled!

I hope my small and simple experience of doing customer development – and particularly interviewing customers – has helped persuade you to get out there and do it yourself, if you aren’t already doing it.

If you think this sounds interesting, and you’d like some help saving time and money while using this process to help build your product or your next feature, do get in touch. I’ll be happy to answer your questions or provide whatever help I can.

Rails Caching Strategies (a Presentation)

| Comments

Tonight I gave a presentation at the Rails Meetup in Seattle on caching strategies with Rails, and I had a great time. I’m convinced Rails developers don’t use caching enough, and we have so many good options for caching in our apps, we really should be avid practitioners of caching. :)

I had a request to put my slides up, so here they are. They are a bit more useful if you have the context of the words I said along with them, but that’s the way these things go, right?

For those of you who were there, I suppose I should apologize for mentioning (so many times) the Airbrake competitor that I recently launched. After the 2nd or so time I mentioned it, it became a bit of a joke to see how many times I could mention it, and I do hope I didn’t annoy you. :)