Recreating WUPHF: API Scaffolding (part 3)

With the web app complete, it’s time to start thinking about how to turn it into an API so that an eventual React-Native app can consume it. In my last post, I talked about the data structure. As a reminder, my models include Users, Recipients, and Messages — pretty straight forward.

Now I have to ask myself: what endpoints do I want to expose? This will ultimately determine the structure of my API. Here’s what I came up with:

Users
POST api/v1/auth (registering)
PUT api/v1/auth (editing account)
POST api/v1/auth/sign_in
DELETE api/v1/auth/sign_out
GET api/v1/auth_validate_token
Recipients
GET api/v1/recipients
POST api/v1/recipients
GET api/v1/recipients/:id
PUT api/vi/recipients/:id
DELETE api/vi/recipients/:id
Messages
POST api/v1/messages

The skeleton is fairly simple. The User model will be handled by Devise Token Auth. Meanwhile, recipients will have every CRUD operation. Remember that a recipient objects exist in a belongs_to relationship with a user. In order for a user to send a message (a Wuphf), they must choose a recipient. Think of this like a contact in your phone book who you send text messages to. Finally, I will only expose a POST operation on messages in order to keep things simple. For now, a user will only be able to send a message but will not be able to do things like view an index of them.

Versioning and Namespacing

You’ll notice that I prepended api/v1 to my endpoints. To implement this, lets jump into the routes:

An example request to fetch our user’s index of recipients might look something like this:

$ curl http://www.wuphf.io/api/v1/recipients

Setting Up Authentication

Before diving into the Recipients and Messages controllers, I want to briefly discuss authentication. A common way to quickly add auth to a Rails app is to use Devise. This is a great solution when you are only creating a web app but can become tricky when you decide to add on an API. There are a number of solutions out there using JSON web tokens but I chose to use the Devise Token Auth gem.

Devise Token Auth

After adding the DTA gem to my gemfile, we run the following to get started:

$ rails g devise_token_auth:install User auth

Because I already have a user model set up with Devise, I need to make changes to the generated migration file to remove any overlap before running rails db:migrate. The new migration file looks something like this:

Back inside of routes, I can add the Devise Token Auth endpoints. Note that we still have a line, devise_for :users outside of our namespace.

If we were to run rails routes | grep api inside of our terminal, we’d see our endpoints

For a deeper look at authentication setup, take a peek at my source code linked at the bottom of this post.

With my routes set up, my controllers folder will be structured like this:

├── controllers
│ ├── api
│ │ ├── v1
│ │ │ └── api_controller.rb
│ │ │ └── messages_controller.rb
│ │ │ └── recipients_controller.rb
│ └── application_controller.rb
│ └── messages_controller.rb
│ └── recipients_controller.rb

That’s it for now! In my next post I will discuss TDD’ing my endpoints.

Check out Wuphf live here and the Github repo here.