Flon, the API maker that uses JSON. It focuses on not doing any magic: it’s just a thin and convenient wrapper over Rack, with a hopefully obvious DSL.
Add this line to your application's Gemfile:
And then execute:
Or install it yourself as:
$ gem install flon
To use Flon, simply make a plain class extending
Flon::DSL. This will put the
router DSL in your class scope.
require 'flon' class MyApi extend :: def initialize @names =  end namespace '/names' do get '/' attr_reader :names post '/new' def add_name(_params, body) @names << body end namespace '/:index' do get '/' def name_by_index(params) @names[params[:index]] end put '/edit' def change_name(params, body) @names[params[:index]] = body end end end end
You can then create a
Flon::Api using this:
api = ::.(MyApi.new)
Note how you initialise the
MyApi normally—you can use this for dependency
injection without a headache.
Flon::Api is a bog-standard Rack app, so you can just use it in
or whatever method you use.
The DSL defines methods for routing based on every HTTP request method, except HEAD, TRACE, OPTIONS, and CONNECT. HEAD is handled by GET routes but the body is discarded.
When you call a routing method, the next method you define will be bound to that route.
get '/route' def get_route # matches GET /route and HEAD /route end post '/route' def post_route # matches POST /route end put '/route' def put_route # matches PUT /route end delete '/route' def delete_route # matches DELETE /route end patch '/route' def patch_route # matches PATCH /route end
Each routing DSL method takes a single route pattern as a
String. The route
pattern is the exact same as Sinatra’s.
The bound method is called when an HTTP request matches that route with that HTTP method.
The method will receive two arguments, in that order:
- A parameters hash, containing the query string parameters and the route parameters;
- A body object, containing the HTTP request’s body parsed with
JSON.parse. For GETs, HEADs, and DELETEs, this will be
You can also namespace routes:
namespace '/users' do get '/' attr_reader :users # GET /users post '/new' def add_user(_params, user) # /users/new @users << user end namespace '/:id' do get def user_by_id(params) # GET /users/:id @users[params[:id]] end put '/edit' def edit_user(params, body) # PUT /users/:id/edit @users[params[:id]] = body end end end
Namespaces are entirely “virtual”, that is, they just concatenate their route patterns with their children, so they’re just there for DRYness.
version method applies a namespace throughout every route:
version '/v1' get '/yes' def yes 'yes' end get '/no' def no 'no' end
/yes will give you a 404, but going to
/v1/yes will give you
"yes". The same thing happens with the
version is just an alias for
Whatever is returned by the route’s method is
#to_json’d and sent back. If
you want to return a custom status code, return a
which takes the status code as the first argument and the body as the second
argument of its constructor:
get '/admin' def admin ::.new(403, 'No. Go away.') end
After checking out the repo, run
bin/setup to install dependencies. Then, run
rake to run rubocop and the tests. You can also run
bin/console for an
interactive prompt that will allow you to experiment.
To install this gem onto your local machine, run
bundle exec rake install. To
release a new version, update the version number in
version.rb, and then run
bundle exec rake release, which will create a git tag for the version, push
git commits and tags, and push the
.gem file to
Bug reports and pull requests are welcome on GitHub at https://github.com/unleashy/flon.
The gem is available as open source under the terms of the MIT License.