Simple Webmachine Extension (2/4): Authorization

This post continues a four-part series that demonstrates how to take the simple os-environment Webmachine resource I wrote last week, and expand it to support modification, authorization, and conditional requests. Today I add basic authorization.

This is the second post in a four-part series about extending a simple Webmachine resource. The first part discussed adding support for the HTTP method PUT.


Something about modification of server state screams, “Password protection!” at me. Let’s guard the PUT method with Basic auth:


-define(AUTH_HEAD, "Basic realm=MyOSEnv").

is_authorized(RD, Ctx) ->
    case wrq:method(RD) of
        'PUT' -> basic_auth(RD, Ctx);
        _     -> {true, RD, Ctx}

basic_auth(RD, Ctx) ->
    case wrq:get_req_header("Authorization", RD) of
        "Basic "++Base64 ->
            case string:tokens(base64:mime_decode_to_string(Base64), ":") of
                ["webmachine", "rules"] -> {true, RD, Ctx};
                _                       -> {?AUTH_HEAD, RD, Ctx}
        _ -> {?AUTH_HEAD, RD, Ctx}

Arbitrary decisions:

  • Only PUT is protected. If GET and HEAD should be protected as well, just replace the body of is_authorized/2 with the body of basic_auth/2

I need to update my curl command if I don’t want to be told I’m unauthorized:

$ curl -u webmachine:rules -X PUT -H "Content-type: application/json" \ 
   http://localhost:8000/_env/MY_VAR -d "\"yay\""

Come back tomorrow for part three, where I add a modicum of atomicity.

Update: part three is up.

Author: Bryan

I'm the creator of Symbology (, BeerRiot (, lots of homebrew, some furniture, and other things. There's more about me at

3 thoughts on “Simple Webmachine Extension (2/4): Authorization”

  1. Enjoying your posts about webmachine.

    How does webmachine knows about is_authorized?
    Does it check if it exists and exported and use it otherwise assume no auth is required?

    Is it possible to authenticate users against credentials stored in a db and keep a session cookie?
    Can I keep the actual auth code in one place and only call it from all the resources if required? Where is the right place to put such auth backend?


  2. Pablo,

    The is_authorized function is one of the many Webmachine Resource Functions, all documented at

    The table on that page shows the default values for each of those functions which will be used if your resource function does not export it.

    It is definitely possible (and not very hard) to do all of the things you ask, including checking auth with a database, using a single central auth function, and so on. However, Webmachine is a Web toolkit and not a framework — it makes no claims to know better than you what the “right” way is to make such application-specific decisions.

  3. Hey, Pablo. Just to echo Justin – yes, webmachine checks to see if you’ve defined is_authorized/2, and uses a default if you haven’t.

    In the implementation of is_authorized, it’s absolutely possible to query some authorization repository, or any other completely arbitrary set of parameters (file existence, time of day, random bit stream, …). It’s a function – compute what you want. 🙂

    And yes, if it makes sense for your app, it’s a great idea to put your auth code in a module that can be called from the is_authorized of many different resources. Reuse through modularity for the win!

Leave a Reply

Fill in your details below or click an icon to log in: Logo

You are commenting using your account. Log Out /  Change )

Google photo

You are commenting using your Google account. Log Out /  Change )

Twitter picture

You are commenting using your Twitter account. Log Out /  Change )

Facebook photo

You are commenting using your Facebook account. Log Out /  Change )

Connecting to %s