In this post, I will demonstrate the techniques used to create our newly open sourced Python HTTP Client, that drives our SendGrid Python library, using a working prototype.

The remainder of this post will reference the following code:

Fluent Interfaces

A fluent interface allows us to create API calls dynamically, without pre-defining all the endpoints. For example, we can use `client.path.to.the.endpoint.get()` for a call to: `GET /path/to/the/endpoint` without defining methods for `path`, `to`, `the`, and `endpoint`.

Method Chaining

To chain our method calls together, in general, we simply return `self`. However, in this case we are returning a new version of the `Fluent` object, because we want to preserve fragments of the url for later reuse see line 8.

Reflection

To capture the method calls dynamically, we need to use Python’s `__getattr__` method (Python 2 docsPython 3 docs), which is called whenever the object can’t find the method you are calling see line 15.

Handling Special Cases

To capture URL parameters and handle Python reserved words, we use the `_()` method see line 6. You pass in a string and receive a new object with the name of your string added to the URL path variable.

References & Acknowledgements

Pythonista

I used this magical tool on my iPhone to whip up the prototype for this idea in minutes while I was on the road. I wish every language had a similar app on iOS.

Kevin Gillette

Kevin proceeded to break my prototype (and my hopes and dreams) with this code:

```python
 client = Fluent()
 x = client.a.b
 y = client b.a
 print x._cache
 print y._cache
 ```

Within minutes, he updated the code and made some adjustments that were so beautiful, a single tear dropped down my cheek.

Birdy

Birdy is a Twitter client that was the first fluent interface I encountered in Python that just worked.

Universal Client

After finding out about Birdy, I searched for a library that already implemented a fluent interface. I found the wonderful Universal Client, which inspired the above code and our Python HTTP Client.

Blog Posts

The following references helped me understand the concepts described in this post:

Thank you for dropping by, and if you decide to build something with this library or have some contributions, please open an issue.

What’s next? Stay tuned as we continue to release similar clients for all the other languages we support (Ruby, PHP, C#, Node.js, Go and Java).

Happy Hacking!



Elmer Thomas is SendGrid's Developer Experience Engineer. His mission is to help SendGrid live up to its slogan: "Email Delivery. Simplified" by improving the lives of developers, both internally and externally. Via all sorts of hackery, of course. Follow his exploits on Twitter and GitHub.