How to Build a Raffle App Using Twilio, WebMatrix and AppHarbor

April 20, 2011
Written by
John Sheehan
Contributor
Opinions expressed by Twilio contributors are their own

Twilio Bug Logo

I spent most of last week at MIX11, one of Microsoft’s big developer conferences. As part of the week’s festivities I was able to showcase RestSharp in a new event Microsoft put on to showcase over 50 different .NET open source projects called Open Source Fest.

While planning for the event I decided I wanted find a way to draw people to stop by my table. I had some spare gadgets I could give away and thought an SMS-based raffle would be a great way to do it. After some thought I settled on the following raffle process:

  1. Give attendees a card with a unique code and a phone number on it
  2. Attendees would text the code to the number to enter the contest
  3. To confirm their entry and allow me to contact them if they won, they would be prompted to send their email address after entering
  4. Give out the cards
  5. Draw a random winner after the event, notify them via email and text message

Since this was a pretty simple app that would be short-lived it was a good candidate for WebMatrix and AppHarbor. WebMatrix is a new, free web development tool from Microsoft that uses a simplified version of ASP.NET with a lot of nice goodies added on to go along with a simple IDE for editing sites and pages. AppHarbor is a new service that is the ‘Heroku for .NET’ with great support for WebMatrix (and other ASP.NET) developed sites.

Generating the Unique Entry Codes

The first step was to generate the unique entry codes that attendees would text in to enter to the contest. I wrote a simple WebMatrix page to generate 1000 random codes and store them in a local SQL database. I checked for duplicates along the way in case my hacky code generator had any collisions. With 4,294,967,296 possible combinations it would be hard to guess any of the 1000 generated. With the page written, I pressed F12 from within the WebMatrix editor to run the page and store the values.

generate.cshtml

@{
    var db = Database.Open("Raffle");
    var rnd = new Random();
    int count = 0;
    while (count < 1000) {
        var code = Guid.NewGuid().ToString().Substring(0,8);

        var existing = db.QuerySingle("SELECT Code FROM Codes WHERE Code = @0", code);
        if (existing == null) {
            db.Execute("INSERT INTO Codes (Code) VALUES(@0)", code);
            count++;
        }
    }
}
<h1>Done</h1>

From Codes to Cards

I copied the generated values of out of the database and into a CSV file and from there did a mail merge to print them out on labels that I affixed to business cards. I also put some of the labels on the handouts I planned to give people at the event.

Handling Entries

Using the Twilio REST API I purchased a phone number after searching for one that ended in MIX. I learned a lesson here about using letters in phone numbers from mobile devices. While building the app I tested it with my iPhone which will happily translate letters to numbers when sending a text message. However, at the event I discovered that some Android and BlackBerry and Windows phones would silently fail if you did this. If you plan on using vanity numbers for a contest, make sure to print the number in its pure form along with the clever one.

With the number purchased I wrote another WebMatrix page to handle the incoming messages. The logic breaks down like as follows.

  1. Check to see if the message contains an email address
    1. If it contains an email address, update all entries from that phone number with the email address
  2. If the message does not contain an email address, it probably contains an entry code
    1. Make sure the code exists
    2. Make sure the code hasn’t already been used
    3. If both checks pass, associate the incoming phone number with the entry code
    4. Prompt for the email address (return to beginning)

The code to make all this happen resides in sms.cshtml:

@{
    var db = Database.Open("Raffle");
    var body = Request.Form["Body"].Trim();
    var @from = Request.Form["From"];
    string response = "";

    if (body.Contains("@")) {
        // response to email address request
        db.Execute("UPDATE Codes SET Email = @0  WHERE ClaimedBy = @1", body, @from);
        response = "Thanks! Your entry is confirmed. You will be notified if you win.";
    }
    else {
        var entry = db.QuerySingle("SELECT Code FROM Codes WHERE Code = @0", body);
        if (entry != null) {
            // check to see if code is already claimed
            var claimed = db.QuerySingle("SELECT Code FROM Codes WHERE Code = @0 AND ClaimedOn IS NOT NULL", body);
            if (claimed != null) {
                response = "Nice try! That code has already been claimed.";
            }
            else {
                db.Execute("UPDATE Codes SET ClaimedBy = @0, ClaimedOn = @1 WHERE Code = @2", @from, DateTime.UtcNow, body);
                response = "Please reply with your email address to confirm your entry and so we can tell you if you win. Your information will not be shared.";
            }
        }
    }

    Response.ContentType = "text/plain";
}
@Html.Raw(response)

Make it Live

I pushed the code up to AppHarbor, grabbed the public URL from my application and assigned it to my phone number.  I also created a database in my AppHarbor application and moved my local copy to the remote one using the WebMatrix database migrate functionality. Voila! The raffle was ready to roll. I handed out over 200 fliers and over 500 cards with entry codes on them. At the end I randomly selected a winner using a crafty SQL query.

Overall the event was a huge success and a lot of fun to be a part of. The raffle added another level of excitement to the proceedings for attendees and best of all, Sean Fao left with a new HTC HD7.

P.S. I also made an infomercial parody for RestSharp for the event. Hope you like it!

[youtube]https://www.youtube.com/watch?v=6duVKnKHc4U[/youtube]