Conversion Analytics Nirvana: Clicky Stats + High Charts

I often find myself being caught in the time sucks of Google Analytics and Clicky Stats. When I code a new feature on a given site, I’m very eager to see how the greater masses of the web use my shiny new feature, but most often I end up sinking too much time clicking around these third party services… when I should be like writing code and stuff.

Conversion Tracking – What Sources Convert?

To me though, the most useful data form any analytics packaging, for an ecommerce site at least, is researching what sources are converting. The uses of this are obvious, and endless, so yesterday I decided to make it a little bit easier for the users of our admin application at The Longboard Store to get in touch with conversion tracking.

Clicky API, Serving Up the JSON Data

I am a big fan of Get Clicky. It is simple, easy to use, and even has some fun features like ‘Spy’ and ‘Big Page’. But the feature I like most is their dead-simple API. So with the final half hour of the day ahead of me yesterday at work, I decided to leverage that API and Highcharts to build a quick view into conversion sources.

Look Out, Psuedo Untested Code

Hackity Hack time ensued, and I whipped up a quick little bit of jQuery and Highcharts to build a Pie Chart of conversion sources.

Essentially I have a button with an id of ‘clicky-chart’, when the user clicks that, the Clicky API is called and a pretty Pie Chart is painted like so:

Make Everyone an Analyst

The wonderful thing about quick features like this is it empowers users of your drab admin tool to really analyze data a bit further. If you dig into the gist above, you can see that when a user clicks on a slice of the pie, a new window is opened to the clicky stats detail page where they can dig into a given group of conversions in finer detail.

Getting this data in front of more users helps foster new ideas, and helps easily identify under-performing marketing channels.

I might abstract out this code a bit to make generating HighChart graphs from the ClickyAPI a bit easier too. We’ll see!

Meet Flipper – A jQuery Plugin to Change Image Src on Hover

Although we do come up with some original ideas at The Longboard Store – we too find inspiration from other online stores as well.  So my boss sent me a link to a Macy’s page and had me hover over some of the product images.

Thus Flipper was born.

Flipper is a super-duper small jQuery plugin that facilitates swapping of image sources on hover. It doesn’t do any fancy fade affects like the one on Macy’s (it could, but why?), but it does pre-load the alternate image for a smooth flipper experience. Now board shoppers can checkout the top and bottom graphics of the boards – all from the same page!

Simple Maps via Google Static Maps

I love maps. When I first laid eyes on Google Maps I was blown away… and when I began dabbling in adding layers of topo maps, I was smitten (I suppose I should have gone into GIS). Anyhow, whenever there is the slightest reason to drop a map on a web page, I am there, Google Maps JavaScript API in hand.

So when I went to add in tracking data on the order status page at The Longboard Store, the new functionality was just screaming for a map. I mean, how cool would it be to watch your order status page, and see where your sweet new Landyahctz Longboard was at?

As such, I dove in, dropping in the JavaScript needed for a map… plopping a marker down… but it kind of dawned on me that it seemed a bit heavy for what is a very basic map. A quick search yielded a Google product that I was unaware of: Static Maps.

Simply put, the API for Static Maps simply involves a standard image tag, where some GET attributes are added into the src tag, and magically a map is shown on your page:

No loading of a JS resource needed, heck, no scripting needed at all. Just a simple url:

http://maps.googleapis.com/maps/api/staticmap?center=45.5626214,-122.6591902&zoom=12&size=567x200&maptype=roadmap
&markers=color:blue%7Clabel:%7C45.5626214,-122.6591902&sensor=false

Crowd Sourcing E-Commerce Photos

There is no longer any doubting the power of mobile phones, and in particular the ability to rapidly share photos with hipster-esque filters applied. After all, we can all cite theone billion$reasons for this.

So when the idea was hatched at thelongboardstore.com to add in some social photo aspect to our site, I was very excited to bring the functionality to life.

Photos By The People, For The People

The concept is rather simple – tap into the massive growing user base of Instagram, and our customer’s mobile devices to power photos for the website. A majority of our customers are in the younger crowd, so why not give them a way to post pictures of what they love – their longboards.

Instagram Photos in Product Detail Page

So all a friend of thelongboardstore.com needs to do is tag any photo with #thelongboardstore within Instagram, and the rest is Rails/Instagram API magic.

Some Code, Some Moderation

To implement the new feature, I leveraged the `official` Instagram ruby gem:

#Gemfile
gem "instagram"

And depending on how you roll with your configuration options, simply add something like so:

#/config/initializers/instagram.rb
Instagram.configure do |config|
config.client_id = "z0mgcl13nt1d"
config.access_token = "s3cr3ts4u1r3ll"
end

For data modeling, I setup a has_many through relationship for Instagram media to our `Product` model. This allows a given photo of a longboard, or a truck, to be attached to many products on the public-facing side of our website. Super social huh?

With all that in place, the process of fetching photos from the Instagram API to persist in our system is so simple it hurts:

instagrams = Instagram.tag_recent_media('thelongboardstore', {:min_tag_id => @last_import_min_tag_id})

The min_tag_id option is a timestamp of sorts that Instagram passes back in their response. This allows the developer to specify a point in time to search for photos.

I iterate over the result set, and add the new photos into a moderation queue in our Admin interface… because you can’t always trust people to do the right thing, and it allows us to attach photos to products.

In Moderation

In-House Efficiencies

The perks of the social photo aspect are obvious for our site visitors. It gives them a way to share their stoke with us, and the rest of the community, and it offers a great glimpse at our products in-action… in a way its almost as good as an in-depth review of the board.

One other awesome thing that has come of the new system though is how we are using Instagram in-house for adding detailed photos to our products. We currently shoot all of our own product photos at the shop – stock photos are just so, well meh. But now, any person in the shop can take a few snapshots of a deck from a different angle, or a close up detail shot of a graphic and add it to the site.

The process is extremely fast, and really fun as well. In the first day alone, two folks at the shop added close to 100 photos. One Hundred. In a single afternoon.

I’m curious to see how our customers start using the system. This morning there were a dozen or so pictures in the queue from them. Furthermore, the Instagram API option of subscribing to tags or geographic areas has got me thinking of a few other applications to use with the service.

Omniauth and Facebook’s #_+_

I’m in the process of implementing a new review system for thelongboardstore.com and am using Omniauth to allow users to sign on via their Facebook account. All is happy and well, but there is a known issue with Facebook where they append ‘#_+_’ to url’s when redirecting a user back to your application.

Being foolish stubborn, I attempted various work-arounds for this one… up to and including nginx re-writes, rack middleware, and cursing. In the end, the functioning work-around is to follow the advice at stackoverflow and reset the hash via javascript:

window.location.hash = ""

As such in my implementation, I have set an instance variable to determine if the user is being redirected from Facebook, and redirecting them upon page load to a new page where the #_+_ doesn’t totally tank my JS:


<% if @show_review -%>
if(window.location.hash.length > 0){
window.location.hash = '';
window.location.href = "<%= @product.url %>?review=1";
}
<% end %>

Ghetto, hack, ugh.

SMS In-Stock Reminders with Twilio

We have all been in that place.  After scouring the web for that latest *must have* toy, and just as you are ready to add to growing debt you see the dreaded words – OUT OF STOCK.

At thelongboardstore.com, such scenarios often resulted in young shredders contacting us via email, or even phone, asking when that super sick Landyachtz Evo deck was going to be available again.  Indeed something had to be done… the consumers want their stuff, so we brewed up a fancy new In-Stock reminder tool to satisfy the retail hunger.

New School and Old Skool

The feature is far from ground-breaking in the online retail world.  Many large e-tailers for years have been offering email-based reminders to shoppers to receive an alert when their desired item is back in stock.

But since a majority of the shoppers at The Longboard Store tend to be in their teens and early twenties, it seemed natural to offer a similar notification service, but via SMS. Additionally, SMS obviously has some major advantages over email-based communications (no-spam folders for the message to die in, immediate customer attention), so we decided to create a system that offered both email and sms notifications.

Sign Up Flow

When a product is out of stock, the user is presented with a call to action to be informed when the inventory is replenished. The design of the page is somewhat muted/grey, and this call to action is rather prominent:

The subsequent page provides the shopper two options for notification, SMS or email. Nothing too exciting here.

When a user chooses the text option, a confirmation sms is sent via the Twilio API (using twilio gem). The user can click the link in the text -or- enter the confirmation code on the web form to confirm their alert subscription.

Waiting Game

Now the consumer waits, iPhone in hand, credit card warming in pocket for that alert to arrive. A few other things that happen during this time though are the buyers can evaluate the number of alerts for given products/brands and adjust buying decisions accordingly.

When our receiving department checks in product, our Rails application determines if the product being checked in has any alert subscriptions, and enqueue’s a job to send notification to our customers that their product is now in stock. Simple. Beautiful.

All About Conversions

Indeed the project was fun to do, and having Twilio in my programmer toolkit made it all possible, but in the online retail space, it all comes down to conversions. So after letting the system run for the first quarter of the year, I decided to analyze the numbers.

To determine if a given alert signup resulted in a paid conversion on our sites, I simply cross-referenced the email/mobile signups from the alert table with those in the billing and shipping addresses on orders. Granted, this won’t catch every possible conversion, it is fairly accurate and accommodates not being able to track conversions with cookies across multiple devices.

  Email Alerts SMS Alerts
Alerts Sent 638 314
Unique Recipients 558 261
Conversions 75 33
Rate 11.75% 10.50%

These conversion rates are obviously well above our overall conversion rate for site visitors, and more than justify the added (albeit minor) expense of sending a text message over an email. I was personally quite surprised to see users signing up for multiple alerts. This makes me think in a future iteration we should allow users to manage all stock alerts via one unified tool – and thus reduce the burden (and cost) of confirming a subscription for each product.

The Future

Ultimately the beauty of this system is opening yet another way to keep a ongoing conversation alive with our customers. Being able to leverage systems like Twilio to connect with first-time and returning customers on mobile devices will continue to be a growing part of our strategy at The Longboard Store.

One of Those Domains

I’m sure most web folk like myself have at least a half dozen of them.  We collect them like paper coffee cups from Starbucks strewn across our desks – once cherished ideas born during a bender – those *awesome* domain names we just had to buy!

The Original Idea

When I first set out on my new career path of a code slanger (circa 2006), I did what most programmers did back then… I created my very own CMS using PHP.  It was rad.  It still runs a few sites around the web actually.  To spare myself some jeering and giggles, I will not furnish a full list, but hey, the thing worked well… and still does.

I built this creation on top of CakePHP and the admin interface was created using a pre 1.0 version of ExtJS.  Super hot.  And the name I gave it was Haiku.  So I bought this domain.  For the longest time when you pulled up haiku2.com all you saw was this:

wing my target
I inflated my princes
under my gravel

So I decided to finally dust it off, install WordPress, and create my very own programming oriented blog.

Why?

Excellent question, and the answer is simple: Blogs Help.  Outside of stackoverflow, I think I have found so many answers to nagging coding questions in the greater blogosphere… so this is going to be my contribution to that grand resource online… and hopefully it will help some random folks out there.

Also, much like reading old code, I get a kick out of reading some of my old blog material.  I will continue to blog about personal items at my Posterous blog, but this will be the business side of my blogging mullet.  Enjoy, and thanks for reading.