Skip to content


Subversion checkout URL

You can clone with
Download ZIP
Commits on Jun 13, 2013
  1. @capflam

    Keep the original request in #arg{} and check it against auth rules

    capflam committed
    Because the request can be rewritten, it could be useful to backup the
    original one. Appmods or Yaws scripts could access it by reading the field
    orig_reg in #arg{}. For CGI scripts, the variable REQUEST_URI is now built
    using the original request (SCRIPT_NAME, PATH_INFO and QUERY_STRING could
    be used to know the info about the rewritten request, if needed).
    The original request is also checked against the authorization rules. So, if
    the request is rewritten, Yaws will check the original request and the
    rewritten one. Access must be granted for both urls to accept the request.
Commits on Feb 11, 2013
  1. @capflam

    Refactor WebSockets and add support of optional callback functions

    capflam committed
    Main changes:
      * Fix some bugs about UTF-8 encoding and messages fragmentation
      * Add support of optional callback functions
      * Add support of many startup options
      * Add support of outgoing fragmented messages
      * Add a websocket testsuite
                                     - * -
    *** bug fixes ***
    First of all, an huge part of yaws_websocket.erl was rewritten to fix bugs
    about the messages fragmentation and the UTF-8 encoding of incoming text
      * UTF-8 encoding
        before, when a text message was fragmented, only the first frame was
        checked and partial UTF-8 sequences were not supported. Now, checks
        are done on each message part and a partial UTF-8 sequence at the end
        of a frame is accumulated and checked with the next frame (for basic
        callback only).
      * Messages fragmentation
        for basic callback modules, because of a buggy mapping between frames
        and messages, the messages fragmentation was almost unusable. To fix
        this, the message handling was rewritten.
    Now, all tests in the autobahn testsuite[1] pass successfully.
                                     - * -
    *** Optional callback functions ***
    Then, from an idea of François de Metz[2], yaws_websocket module was
    extended to support optional callback functions. See the documentation for
    details (www/websockets.yaws).
    Quickly, optional callback functions are:
      * Module:init/1           (for basic and advanced callback modules)
      * Module:terminate/2      (for basic and advanced callback modules)
      * Module:handle_open/2    (for basic and advanced callback modules)
      * Module:handle_info/2    (for basic and advanced callback modules)
      * Module:handle_message/2 (for basic callback modules only, used in place
                                 of Module:handle_message/1)
    Thanks to Pablo Vieytes[3] which added handle_info to optional callback
                                     - * -
    *** Startup options ***
    To start a websocket process a script must return the following term from
    its out/1 function:
      {websocket, CallbackMod, Options}
    where 'Options' is a (possibly empty) proplist. Following parameters are
      * {origin, Orig}
      * {callback, Type}
      * {keepalive, Boolean}
      * {keepalive_timeout, Tout}
      * {keepalive_grace_period, Time}
      * {drop_on_timeout, Boolean}
      * {close_timeout, Tout}
      * {close_if_unmasked, Boolean}
      * {max_frame_size, Int}
      * {max_message_size, Int}
      * {auto_fragment_message, Boolean}
      * {auto_fragment_threshold, Int}
    See the documentation for details (www/websockets.yaws).
                                     - * -
    *** Outgoing fragmented messages ***
    A callback module can now send fragmented messages to clients using the
    record #ws_frame{}:
     #ws_frame{fin     = true,  %% true | false
               rsv     = 0,
               opcode,          %% text | binary | continuation...
               payload = <<>>}. %% binary(), unmasked data
    [2] #99
Commits on Jul 10, 2012
  1. @capflam

    Refactor Set-Cookie/Cookie header parsing to follow RFC6265

    capflam committed
    RFC6265 obsoletes RFC2965 and RFC2109. #setcookie{} and #cookie{} are
    changed to reflect this new RFC. So, yaws_api:parse_set_cookie/1 and
    yaws_api:parse_cookie/1 are refactored accordingly:
    * yaws_api:parse_set_cookie/1: Because RFC2109 and RFC2965 are still used,
      we try to be backward compatible with these old RFCs. So this function
      returns a #setcookie{} record when only one cookie is found else it returns
      a list of #setcookie{} records.
      in RFC2109 and RFC2965, cookies are separated by comma. So, comma is
      forbidden in 'path-av' and 'extension-av' except for double-quoted value.
      The parsing are not really strict because of the compatibility and can lead
      to unwanted behaviors.
      Old attributes (like 'Comment' or 'Port') are still parsed and can be
      found into #setcookie.extensions field.
    * yaws_api:parse_cookie/1: This function follows the RFC6265, so all cookie
      attributes (like '$Domain' or '$Path') are parsed like any other cookie.
Commits on Jul 4, 2012
  1. @capflam

    Fix parse_set_cookie/1 and format_set_cookie/1 functions

    capflam committed
    1. According to the RFCs 2109 and 2965, multiple cookies can be set in a
    single 'Set-Cookie' header. So, yaws_api:parse_set_cookie/1 now returns a
    list of #setcookie{} records. If no cookie was found or if an error occurred,
    it returns []. The parsing is also improved.
    Note that this fix breaks the compatibility with previous versions.
    2. In yaws_api:format_set_cookie/1, options are now always formated as
    3. 2 new functions are added, yaws_api:parse_cookie/1 and
    yaws_api:format_cookie/1, to parse and format 'Cookie' headers. To let these
    functions to work, the #cookie{} record was introduced.
    Documentation and testsuite are updated accordingly.
Commits on May 24, 2011
  1. @capflam @vinoski

    arg_rewrite mods can now return HTTP responses (capflam)

    capflam committed with vinoski
    Module used to rewrite arg records can now return any HTTP
    response. This can be used to redirect requests or to return an
    error. To do so, such a module must set the element #arg.state using
    the record #rewrite_response{}. The record #rewrite_response{}
    contains 3 elements:
      status: any valid HTTP status code
      headers: a list of {header, H}
      content: an iolist
    For example, to do an unconditional redirect to,
    you can use the module simple_redir_mod.erl:
      arg_rewrite(Arg) ->
        L = "",
        H = [{header, {location, L}}],
        RwResp = #rewrite_response{status=301, headers=H}
Something went wrong with that request. Please try again.