Commits

Justin Sheehy committed d0cbd9e

Automated commit message

Comments (0)

Files changed (1)

ExampleResources.wiki

-The simplest possible example is the one produced via the [[QuickStart]].
-
-For an example of a read/write filesystem server showing several interesting features and supporting GET, PUT, DELETE, and POST, see [[FixThisLink|demo_fs_resource].
-
-For a very simple resource demonstrating content negotiation, basic auth, and some caching headers, see [[FixThisLink|webmachine_demo_resource]].
-
-Some example code from webmachine_demo_resource follows.
-
-The simplest working resource could export only one function in addition to init/1:
-
-{{{
-#!erlang
-to_html(ReqData, Context) -> {"<html><body>Hello, new world</body></html>", ReqData, Context}.
-}}}
-
-That's it. That resource will respond to all valid GET requests with the exact same response.
-
-Many interesting bits of HTTP are handled automatically by Webmachine. For instance, if a client sends a request to that trivial resource with an Accept header that does not allow for a text/html response, they will receive a 406 Not Acceptable.
-
-Suppose I wanted to serve a plaintext client as well. I could note that I provide more than just HTML:
-
-{{{
-#!erlang
-content_types_provided(ReqData, Context) ->
-   {[{"text/html", to_html},{"text/plain",to_text}], ReqData, Context}.
-}}}
-
-I already have my HTML representation produced, so I add a text one:
-(and while I'm at it, I'll show that it's trivial to produce dynamic content as well)
-
-{{{
-#!erlang
-to_text(ReqData, Context) ->
-   webmachine_reqdata:disp_path(ReqData),
-   Body = io_lib:format("Hello ~p text~n", [Path]),
-   {Body, ReqData, Context}.
-}}}
-
-Now that this resource provides multiple media types, it automatically performs conneg:
-
-{{{
-$ telnet localhost 8000
-Connected to localhost.
-Escape character is '^]'.
-GET /demo/a/resource/path HTTP/1.1
-Accept: text/plain
-
-HTTP/1.1 200 OK
-Vary: Accept
-Server: MochiWeb/1.1 WebMachine/0.12
-Date: Tue, 23 Sep 2008 00:47:55 GMT
-Content-Type: text/plain
-Content-Length: 29
-
-Hello "a/resource/path" text
-}}}
-
-What about authorization? Webmachine resources default to assuming the client is authorized, but that can easily be overridden. Here's an overly simplistic but illustrative example:
-
-{{{
-#!erlang
-is_authorized(ReqData, Context) ->
-    case webmachine_reqdata:disp_path(ReqData) of
-        "authdemo" -> 
-            case webmachine_reqdata:get_req_header("authorization", ReqData) of
-                "Basic "++Base64 ->
-                    Str = base64:mime_decode_to_string(Base64),
-                    case string:tokens(Str, ":") of
-                        ["authdemo", "demo1"] ->
-                            {true, ReqData, Context};
-                        _ ->
-                            {"Basic realm=webmachine", ReqData, Context}
-                    end;
-                _ ->
-                    {"Basic realm=webmachine", ReqData, Context}
-            end;
-        _ -> {true, ReqData, Context}
-    end.
-}}}
-
-With that function in the resource, all paths except {{{ /authdemo }}} from this resource's root are authorized. For that one path, the UA will be asked to do basic authorization with the user/pass of authdemo/demo1. It should go without saying that this isn't quite the same function that we use in our real apps, but it is nice and simple.
-
-HTTP caching support is also quite easy, with functions allowing resources to define {{{ last_modified }}} , {{{ expires }}}, and {{{ generate_etag }}}. For instance, since representations of this resource vary only by URI Path, I could use an extremely simple entity tag unfit for most real applications but sufficient for this example:
-
-{{{
-#!erlang
-generate_etag(ReqData, Context) ->
-    {ReqData#wm_reqdata.path, ReqData, Context}.
-}}}
-
-And now the response from our earlier request is appropriately entity-tagged:
-
-{{{
-HTTP/1.1 200 OK
-Vary: Accept
-Server: MochiWeb/1.1 WebMachine/0.12 (A Very Small Sandwich)
-ETag: a/resource/path
-Date: Tue, 23 Sep 2008 01:30:20 GMT
-Content-Type: text/plain
-Content-Length: 29
-}}}
-
-For more details, read the source of the resources linked at the top of this page. 
-
+The simplest possible example is the one produced via the [[QuickStart]].
+
+For an example of a read/write filesystem server showing several interesting features and supporting GET, PUT, DELETE, and POST, see [[FixThisLink|demo_fs_resource].
+
+For a very simple resource demonstrating content negotiation, basic auth, and some caching headers, see [[FixThisLink|webmachine_demo_resource]].
+
+Some example code from webmachine_demo_resource follows.
+
+The simplest working resource could export only one function in addition to init/1:
+
+{{{
+#!erlang
+-module(webmachine_demo_resource).
+-export([init/1, to_html/2]).
+-include_lib("webmachine/include/webmachine.hrl").
+
+init([]) -> {ok, undefined}.
+
+to_html(ReqData, Context) -> {"<html><body>Hello, new world</body></html>", ReqData, Context}.
+}}}
+
+That's really it -- a working webmachine resource. That resource will respond to all valid GET requests with the exact same response.
+
+Many interesting bits of HTTP are handled automatically by Webmachine. For instance, if a client sends a request to that trivial resource with an Accept header that does not allow for a text/html response, they will receive a 406 Not Acceptable.
+
+Suppose I wanted to serve a plaintext client as well. I could note that I provide more than just HTML:
+
+{{{
+#!erlang
+content_types_provided(ReqData, Context) ->
+   {[{"text/html", to_html},{"text/plain",to_text}], ReqData, Context}.
+}}}
+
+I already have my HTML representation produced, so I add a text one:
+(and while I'm at it, I'll show that it's trivial to produce dynamic content as well)
+
+{{{
+#!erlang
+to_text(ReqData, Context) ->
+   webmachine_reqdata:disp_path(ReqData),
+   Body = io_lib:format("Hello ~p text~n", [Path]),
+   {Body, ReqData, Context}.
+}}}
+
+Now that this resource provides multiple media types, it automatically performs conneg:
+
+{{{
+$ telnet localhost 8000
+Connected to localhost.
+Escape character is '^]'.
+GET /demo/a/resource/path HTTP/1.1
+Accept: text/plain
+
+HTTP/1.1 200 OK
+Vary: Accept
+Server: MochiWeb/1.1 WebMachine/0.12
+Date: Tue, 23 Sep 2008 00:47:55 GMT
+Content-Type: text/plain
+Content-Length: 29
+
+Hello "a/resource/path" text
+}}}
+
+What about authorization? Webmachine resources default to assuming the client is authorized, but that can easily be overridden. Here's an overly simplistic but illustrative example:
+
+{{{
+#!erlang
+is_authorized(ReqData, Context) ->
+    case webmachine_reqdata:disp_path(ReqData) of
+        "authdemo" -> 
+            case webmachine_reqdata:get_req_header("authorization", ReqData) of
+                "Basic "++Base64 ->
+                    Str = base64:mime_decode_to_string(Base64),
+                    case string:tokens(Str, ":") of
+                        ["authdemo", "demo1"] ->
+                            {true, ReqData, Context};
+                        _ ->
+                            {"Basic realm=webmachine", ReqData, Context}
+                    end;
+                _ ->
+                    {"Basic realm=webmachine", ReqData, Context}
+            end;
+        _ -> {true, ReqData, Context}
+    end.
+}}}
+
+With that function in the resource, all paths except {{{ /authdemo }}} from this resource's root are authorized. For that one path, the UA will be asked to do basic authorization with the user/pass of authdemo/demo1. It should go without saying that this isn't quite the same function that we use in our real apps, but it is nice and simple.
+
+HTTP caching support is also quite easy, with functions allowing resources to define {{{ last_modified }}} , {{{ expires }}}, and {{{ generate_etag }}}. For instance, since representations of this resource vary only by URI Path, I could use an extremely simple entity tag unfit for most real applications but sufficient for this example:
+
+{{{
+#!erlang
+generate_etag(ReqData, Context) ->
+    {ReqData#wm_reqdata.path, ReqData, Context}.
+}}}
+
+And now the response from our earlier request is appropriately entity-tagged:
+
+{{{
+HTTP/1.1 200 OK
+Vary: Accept
+Server: MochiWeb/1.1 WebMachine/0.12 (A Very Small Sandwich)
+ETag: a/resource/path
+Date: Tue, 23 Sep 2008 01:30:20 GMT
+Content-Type: text/plain
+Content-Length: 29
+}}}
+
+For more details, read the source of the resources linked at the top of this page. 
+