Use Exim and pipes to replicate MailGun routes

Over the last month or so I’ve been working with a friend of mine on a little side project (more on that later). During the course of the project, we ended up using Mailgun to receive email which was then passed to a PHP script using Mailgun routes.

Mailgun was pretty easy to setup and things were great but unfortunately in the last day or so our free app started creeping over the 200 message/day limit on the Mailgun free tier. Since the app is currently free, we couldn’t really justify paying the $19/mon minimum for the first Mailgun tier so I started exploring self-hosted options.

After a big of Googling, the first thing that caught my eye was the LamsonProject. From my understanding, Lamson basically provides a SMTP server which binds to a MVC application framework. After checking out the docs and the code it seemed like Lamson would allow you to build a RESTful application that responded to SMTP messages instead of HTTP requests. It certainly seems like a cool project but seemed like a bit overkill for what I needed to do.

Going further down the rabbit hole, I found out that the Exim allows messages to be delivered to a regular *nix process via a pipe and that the configuration was supposedly relatively straightforward under Ubuntu. Given that, I decided to give it a shot, it turned out to be relatively easy to setup but here is a quick rundown.

Step 1: Setup Exim

By default, Ubuntu systems are configured with sendmail and only setup to receive local mail. You’ll need to remove sendmail, install Exim, and then configure it.

To do this you’ll roughly need to run the following:

sudo apt-get remove sendmail
# for some reason the dependencies aren't being installed correctly
# see http://ubuntuforums.org/showthread.php?p=10411454
sudo apt-get install exim4-base exim4-config
sudo apt-get install exim4
sudo dpkg-reconfigure exim4-config

Next, follow the guide on https://help.ubuntu.com/8.04/installation-guide/hppa/mail-setup.html to configure Exim.

Step 2: Configure Pipes and Aliases

Per https://answers.launchpad.net/ubuntu/+source/mailman/+question/120447 it turns out something isn’t enabled in the default Ubuntu configuration of Exim. To solve this, I added the following

.ifndef SYSTEM_ALIASES_PIPE_TRANSPORT
SYSTEM_ALIASES_PIPE_TRANSPORT = address_pipe
SYSTEM_ALIASES_USER = Debian-exim
SYSTEM_ALIASES_GROUP = daemon
.endif

Into the bottom of /etc/exim4/conf.d/transport/30_exim4-config_address_pipe

After you edit an Exim setting, you’ll need to always run the following for the settings to take effect:

sudo update-exim4.conf.template -r
sudo update-exim4.conf
udo service exim4 restart

Next, you’ll need to enable the catch-all router configuration. This was surprisingly difficult to track down how to do:

Per, http://pontus.ullgren.com/view/Setting_SMTP_server_development_test_server_running_Ubuntu you need to create a file at /etc/exim4/conf.d/router/950_exim4-config_catchall containing

catch_all:
   debug_print = "R: catch_all for $local_part@$domain"
   driver = redirect
   data = ${lookup{*}lsearch{/etc/aliases}}
   # NOTE: I added this line for the catch all pipes to work
   pipe_transport = address_pipe

Finally, add a catch-all alias that pipes to a script to your /etc/aliases file. Mine looks like:

*: "|/home/ubuntu/exim4.php"

Step 2: The PHP script

I did this with PHP since my original Mailgun script was in PHP but anything should work. Key notes, the script needs to be accessible AND executable by the Exim user. Also, you’ll need the appropriate shebang to make the script work without a named interpreter.

Your script is going to receive raw SMTP email so you’ll need to parse that out to do anything meaningful with it. Thankfully there are plenty of libraries to do this. I ended up using MailParse along with PHP MimeMail Parse to abstract the nitty gritty into some cleaner object oriented code.

The part of my script that accepts and parses the email looks like:

From there, you’d be free to do anything you wanted with $msgInfo, just like on the receiving end of a Mailgun route.

Anyway, as always let me know if you have any feedback, questions, or comments.

BigCommerce Bulk Coupon Code Importer

A buddy of mine has an eCommerce storefront through BigCommerce, a hosted eCommerce solution. He was looking to run a Gilt City promotion, so he would have to import ~150 coupon codes into BigCommerce.

My friend spent some time looking around for an import codes feature and I would have assumed that a solution like BigCommerce would support a CSV import for coupon codes as well. However, we Googl’ed around a bit and it turns out BigCommerce does not support CSV imports for coupon codes. We stumbled upon this discussion on the BigCommerce forums discussing this shortcoming at length.

On the forum thread, someone had previously developed an iMacros script to automate importing the codes. Unfortunately, I tried using the iMacros script without any success. It looks like BigCommerce has updated the HTML on the page which is breaking the script. Anyway, looking at the iMacro and the opaque syntax I decided it would be easier to whip together a Chrome extension to automate creating coupon codes so decided to move forward with that.

Chrome extensions naturally lend themselves to automating things like this since it’s pretty straightforward to use the background page to maintain any state and hold variables and then use a content script to manipulate the DOM of the page and submit any forms that you need to.

You can grab the extension here http://setfive.com/misc/BigComm Importer.crx you’ll obviously need to be running Google Chrome for it to work.

Also, fork it at https://github.com/adatta02/bigcommerce-coupon-importer

What it does is add a “Bulk Import” button to the “Coupon Codes” page on your BigCommerce site – http://[yourstore].mybigcommerce.com/admin/index.php?ToDo=viewCoupons

If you click that button, a copy of the “add code” form will be displayed along with a textbox. You’ll just need to fill out the form, enter a list of coupon codes you want to create – one per line, and then click “Start Import”.

Your browser will automatically go through and create all your coupon codes. Thats it!

As always, let me know if you run into any issues or have any comments.

Be Responsive: A History of Responsive Design

During the last two years the number of mobile devices has grown at an exponential pace, with one Cisco estimate (http://bit.ly/zVdFJD) predicting more mobile connected devices than people by the end of 2012. Due to this growth, providing a first class mobile web experience has become increasingly important and is now a paramount concern for websites. Union Square Ventures’ Fred Wilson went as far as to point out that new web apps are commonly designed “mobile first web second” (http://bit.ly/gQTtBp)

Within the last year a technique known as “responsive design” has become an increasingly popular way to tackle “mobile vs. desktop” web design issues. There have been several reasons for this rise in popularity which we’ll talk about after an abridged history of the mobile web.

How did we get here? Well it all started with WAP… Back in the dark days of the mobile web, well before the average consumer was accessing the Internet from a cellphone the majority of web content was served via a technology called the Wireless Application Protocol. Even I am to young to really have experienced it in all of its glory but the “Criticisms” page on Wikpedia should convey just how awful it was – http://bit.ly/wWxY2c Big takeaways? Imagine writing websites in XML, oh and it has to validate.

Anyway, fast forward a couple of years and vaguely recognizable devices are slowly starting to come online. From the Nokia Symbians, to Palm, and of course the venerable Blackberry mobile devices are beginning to access the nascent mobile web (yay!). The problem? The browsers on these devices were severely limited in terms of CSS and Javascript support, standards compatibility, and available bandwidth. As a result of these limitations, developers chose to basically develop “stripped down” basic HTML versions of sites to present on mobile devices.

One last trip in the DeLorean and we’re zooming from the initial release of the iPhone during the summer of 2007 to today with thousands of smart phone and tablet models and billions of connected devices. During this period, developers tended to build specific “mobile” sites which were usually an entirely separate HTML/CSS/JS(kinda?) code base from their desktop sites. Understandably, this situation was less than ideal since at the minimum it meant maintaining two code bases and the mobile site often lacked the full functionality of the desktop site. Additionally, as both desktop and mobile browser development rapidly progressed consumers began to expect a consistent experience across their devices.

So how do we address these issues and improve mobile user experience? Enter, “responsive design”. The central tenant of responsive design is that you (the designer/developer) should be able to use the same HTML, CSS, and Javascript to serve devices with different screen sizes and resolutions. The idea is that your layout should be able to respond by adapting the it’s presentation layer depending on any number of factors.

The key technology this process relies upon are Media Queries. Fully adopted by CSS3, media queries allow CSS directives to be conditionally applied depending on the result of a boolean query. In practice, this means a single CSS stylesheet can contain one set of directives for a 480px screen as well as different directives for a 1200px screen. Lets look at an example. If you open http://www.agentvita.com/ and then progressively shrink your browser window you’ll see that the elements dynamically adjust depending on the size of the screen.

Well that’s some history and a quick demonstration, now for some nitty implementation gritty details. Unfortunately, there’s no “magic bullet” to automatically take a standard desktop layout and responsively adapt it for different screen sizes. In my opinion the best approach is to start with a solid framework, keep your markup clean, and of course be cognizant that you’re planning to adapt the layout for different screen sizes. Or if you’re feeling brave, start with the mobile layout first and then progressively enhance the layout as your screen size increases.

Here are some specific resources to get started:

Red Wings & Michigan Lottery cross promo launched!

Hope everyone survived the first week of 2012 unscathed. Just wanted to announce that we helped the Detroit Red Wings and the Michigan State Lottery launch a Facebook promotion. It’s a pretty neat deal, all you have to do is LIKE the MI Lottery page and submit your information to be entered to win a Zamboni ride. And honestly, who doesn’t love a Zamboni ride.

The promo is live here https://www.facebook.com/MichiganLottery

Unfortunately, its only open to Michigan residents.

Boomerang via @fredwilson and @cdixon

Hope everyone had a great Christmas and that you’re gearing up for a great New Years!

Anyway, I picked up a Kindle Fire for Christmas and decided to use it as an eReader at least once in its life. I had remembered seeing Boomerang by Michael Lewis recommended by both Fred Wilson and Chris Dixon so I figured it must be worth checking out.

The book is a short, easy read but it offers a fascinating perspective on the global financial crisis through several different viewpoints. As Chris pointed out, theres also a couple of funny anecdotes and bizarre cultural highlights. If you have some time to kill, I’d definitely recommend picking up Boomerang and giving it a once over.