Monday, December 5, 2011

Tips for First Time Braintree Integrators

I just finished building CollegeSet. A web application for helping students pay for college (It's nonprofit. It's fun. go make a donation!). We use Braintree Payments for our gateway. I had a great experience building against their API and I'll definitely use them again! Here are a few tips to anyone else who is just starting to integrate with Braintree.

Read the examples


Their github profile has sample applications in many different languages. Don't start yours without spending some serious time with theirs!

TDD it


This part of your application is too important not to test. Unfortunately, it is one of the more difficult parts to test. I found that a good mocking library was enough to let me test most of the controller logic around my payments. I fell short of doing end to end testing like this person describes.

Give yourself time


It took us 3 weeks to get our application approved for use with Braintree. (The holdup wasn't Braintree.) They audit your site and require the terms of service, so we ended up waiting for lawyers and clients to hash out those details before we could get approval. You do get instant access to their sandbox though, which means you can do development in parallel with the approval process. Don't wait until the last minute!

Room for Improvement


Overall Braintree was the best of all the solutions I researched. Their "transparent redirect" helps you minimize your PCI compliance exposure while maintaining a great user experience (no IFrame), and their API's are great. Of course nobody's perfect... Here is my wishlist for three things that I would like to see from Braintree in the future.

  • A braintree test-proxy gem for easier integration testing.

  • Sample controller and integration tests in the sample applications.

  • A developer console in the sandbox for examining requests and responses.



Edit: ThoughtBot has created Fake Braintree as a way to do braintree integration testing. I'm going to give it a shot.

Saturday, November 12, 2011

Renaming Attributes the Sneaky Way

The names of your models and their attributes are profoundly important to a Rails application. They become the namesakes to everything else: controllers, views, routes, tests. Users of your application are going to see these names in urls, form fields and validation messages. A few minutes early on can save you hours of find/replace, file renames and broken tests down the road. Sometimes you don't have the luxury of a rename. The shortcut is localization! Let's say your application has a User model with an attribute 'sex'. Those 'Sex can't be blank' validation messages are causing your users existential crises. Let's rename sex to gender. Edit en.yml and add the following:


en:
activerecord:
attributes:
user:
sex: Gender


All your validation and form fields are magically renamed. Voila!

Wednesday, June 29, 2011

Publishing in the Chrome Web Store

My sourdough hydration calculator is now freely available via Google's Chrome Web Store. The app is just HTML and JS so converting it to be a Chrome app is as simple as adding a manifest file and zipping everything up! No real work involved. It felt pretty cool to throw my app out there and to see it in the search results immediately. It is the only app out there for makers of pain au levain. #FirstToMarket The Chrome web store is great! I love that if you buy an app you can cancel your purchase within the first 30 minutes. Apple should adopt that consumer friendly policy instead of their lemmings approach. It keeps you from getting scammed by vendors of broken, half-assed apps. I'd like them to develop their Developer dashboard a bit more. The dual purpose "Publish" link is confusing. It took me an hour to figure out I needed to click publish (the go live button) in order to make it available to test users. And as with everything Google if their documentation doesn't have it you are stuck begging in a Google group for answers. No such thing as real live customer support at the G.

Sunday, February 20, 2011

Dynamic Tweet Button Text and Counting Tweets

I deployed a new version of Hydration = which adds a little tweet button to the footer. One thing I wanted to do was make the text of the tweet different depending on what the user has done on the site. Since the site is just javascript and one static page I wanted to find a simple way to update the value that twitter sends for the tweet text. Unfortunately Twitter uses an iframe for this. The trick is to realize that the src attribute of the iframe contains the tweet message. So you can just update that with jQuery. That works pretty well. There is a slight annoyance because changing the src of the iframe causes the iframe to reload.

On a totally separate note. Another thing I bumped up against was getting the tweet count to increment. Beware URL's with a trailing slash. Twitter must strip that out of the URL before they use it as a key and so if your data-url attribute has a trailing slash the tweet count doesn't work.

Tuesday, February 8, 2011

The type casting edge case in Rails validation

Validation is one of the things Rails does very well. Most of the time you can manage your validation with one of the standard declarative validations. Occasionally you need something custom, but even then life is good and your custom validation is as simple as writing a two or three line method. However, there are edge cases and I'm going to talk about one. Let's start with the request. Request parameters come in to your application as strings and rails automatically maps them to the type prescribed by your DB.

If you aren't thinking about this (and it is easy not to think about it) you can be in for some surprises. If your field is an integer, but a user supplies a non numeric string, it will get type cast as zero. If your field is a date, but a user supplies an invalid date, like February 31, you will get March 3rd. If they were really off and supplied February 43rd, you will just get nil.

This leads to some confusing behavior. Imagine you have an optional date of birth field on a form and a manual validation to ensure that date is in the past. If somebody enters February 43rd 1969 as their date because of type casting the field is set to nil and nothing will happen. Which is weird.

If we want to give our users meaningful feedback about their dates we are going to have to do something about this. Looking at stackoverflow. Most people trying to solve this problem just override the accessor. Bad! Changing the behavior of an accessor in the best case is introducing unexpected behavior to your models and in the worst case will cause bugs because that isn't how a standard activerecord object works.

The Rails folks have already considered this problem and so there is a feature that works around it. It seems not too many people know about it, but it is documented! ActiveRecord has alternate versions of every attribute. They are aptly named *_before_type_cast. So in our case date_of_birth_before_type_cast would contain the string 2/43/1969. And you can use that value to give a more accurate error message. I lost a couple hours the other day researching this problem, but lesson learned and I thought I would spread the good word about _before_type_cast.