Replace temporary test name

Replace temporary test name

Whoops...

# /api/Data Structures/Batman.Object

`Batman.Object` is the superclass for virtually all objects in a batman.js application. `Batman.Object` mixes in:

- `Batman.Observable` for `get`, `set`, `observe` and others
- `Batman.EventEmitter` for `on`, `off`, `fire` and others

See [`Batman.Object Accessors`](/docs/api/batman.object_accessors.html) for a full description of `@accessor`, which defines properties on `Batman.Object`s.

## @accessor([keys...], objectOrFunction)

If `keys` is empty, defines a new default accessor for instances of the object, otherwise defines a new accessor on instances of the `Object` for `keys`.

`objectOrFunction` may be:

- An object with `get`, `set`, and/or `unset` keys whose values are functions which implement those operations.
- A function which will be treated as the `get` key of the accessor object.

## @classAccessor([keys...], objectOrFunction)

Follows the pattern of `Bamtan.Object.accessor`, but defines the accessor on the class (constructor) instead of on instances of the object.

    test '@classAccessor defines an accessor on the class', ->
      class WayneManor extends Batman.Object
        @classAccessor 'address', -> "123 Wayne Dr."

      equal WayneManor.get('address'), "123 Wayne Dr."
      # Wayne Manor burned down...
      equal (new WayneManor(isRebuilt: true)).constructor.get('address'), "123 Wayne Dr."

## @mixin(objects...) : prototype

Mixes in `objects` to the `Object`'s prototype. Keys from `objects` are applied with `set`. If any of `objects` has an `initialize` function, it will be called with the prototype being mixed into.

_Note_: `@mixin`, similar to `@accessor`, applies to all instances of a class. If you need to mix in to the class itself, look at `classMixin`. `@mixin` is intended for use during the class definition of a `Batman.Object` subclass.

    test '@mixin extends the prototype of a Batman.Object subclass', ->
      FishBehaviour =
        canBreatheUnderwater: true
      MammalBehaviour =
        initialize: ->
          @set('isMammal', true)
        canBreatheAboveWater: true

      class Platypus extends Batman.Object
        @mixin FishBehaviour, MammalBehaviour

      platypus = new Platypus
      ok platypus.get('isMammal'), "the initialize function is called with the target prototype"
      ok platypus.get('canBreatheAboveWater')
      ok platypus.get('canBreatheUnderwater')

## @classMixin(objects...) : this

`@classMixin` mixes `objects` into the class (constructor) in the same way that `@mixin` mixes into the prototype.

    test '@classMixin extends the Batman.Object subclass', ->
      Singleton =
        initialze: (subject) ->
          subject.accessor 'instance', -> new subject

      class Highlander extends Batman.Object
        @classMixin Singleton

      instance = Highlander.get('instance')
      ok instance == Highlander.get('instance'), "There can only be one."

## @observeAll(key, callback : function) : prototype

`@observeAll` extends the `Batman.Object` implementation of `Batman.Observable` with the ability to observe all instances of the class (and subclasses). Observers attached with `@observeAll` function exactly as if they were attached to the object directly. Returns the prototype of the class.

_Note_: `@observeAll` is intended to be used during the class definition for a `Batman.Object` subclass, but it can be called after the class has been defined as a function on the class. It supports being called after instances of the class have been instantiated as well.

    test "@observeAll attaches handlers which get called upon change", ->
      results = []
      class Song extends Batman.Object
        @observeAll 'length', (newValue, oldValue) -> results.push newValue

      song = new Song({length: 340, bpm: 120})
      equal song.set('length', 200), 200
      deepEqual results[1], 200

    test "@observeAll can attach handlers after instance instantiation", ->
      results = []
      class Song extends Batman.Object

      song = new Song({length: 340, bpm: 120})
      equal song.set('length', 360), 360
      deepEqual results[0], undefined
      Song.observeAll 'length', (newValue, oldValue) -> results.push newValue
      equal song.set('length', 200), 200
      deepEqual results[0], 200

## @delegate(properties..., options)

Delegates `properties` to `options.to` by creating new accessors for `properties` which call `to.get(property)`. `options` must include a `to` Object.

## @singleton(singletonMethodName[="sharedInstance"])

Shorthand for [singleton classes](http://en.wikipedia.org/wiki/Singleton_pattern). Defines a class accessor `singletonMethodName` which returns the singleton instance.

## @wrapAccessor([keys...,] wrapperFunction: Function)

Defines a *wrap accessor* for the given keys. These accessors are intended to
extend an existing accessor or property by wrapping calls to `get`/`set`/`unset`.

`wrapperFunction` is called immediately, and should return an object with the
same format as an accessor definition. It is passed an object that represents
the original accessor being wrapped, called `core`.

Some trivial examples:

    test "@wrapAccessor can be used to extend get functionality", ->
      class Product extends Batman.Object
        @wrapAccessor 'title', (core) ->
          get: (key) -> 'Product ' + core.get.call(this, key) # Call the original get function.

      foo = new Product(title: 'Foo')
      equal foo.get('title'), 'Product Foo'

    test "@wrapAccessor can be used to extend set functionality", ->
      class Product extends Batman.Object
        @wrapAccessor 'title', (core) ->
          set: (key, value) ->
            core.set.call(this, key, value.toUpperCase()) # Call the original set function, with different arguments.

      foo = new Product(title: 'Product Foo')
      equal foo.get('title'), 'PRODUCT FOO'

Here's a real-world example of a fairly common use-case.
`Product` has a `handle`, which is the token used to identify the product in a
URL. If the user hasn't set a custom handle, then the handle should be generated
from the title. If they do set a custom handle, then changes to the title should
not affect the handle.

    test "@wrapAccessor implementation of generating resource handles", ->
      handleize = (value) -> value?.toLowerCase().replace(/\W+/g, '-')

      class Product extends Batman.Object
        @wrapAccessor 'handle', (core) ->
          get: -> core.get.apply(@, arguments) || handleize(@get('title'))

        @wrapAccessor 'title', (core) ->
          set: (key, value) ->
            if @get('handle') == handleize(@get('title'))
              @set('handle', handleize(value))

            core.set.call(this, key, value)

      foo = new Product(title: 'Product Foo!!')
      equal foo.get('handle'), 'product-foo-' # Handle is automatically set.

      foo.set('title', 'Product Bar')
      equal foo.get('handle'), 'product-bar' # Handle is automatically set again.

      foo.set('handle', 'custom-handle') # User defines a custom handle for this product...
      foo.set('title', 'Product Foo!!')
      equal foo.get('handle'), 'custom-handle' # so now it's not automatically set.

`@wrapAccessor` may be called with no keys to wrap *all* accessors.

## @wrapClassAccessor([keys...,] wrapperFunction: Function )

Like `@wrapAccessor`, but to wrap a class-level accessor.

## ::wrapAccessor([keys...,] wrapperFunction)

Like `@wrapAccessor`, but wraps an accessor on a single instance.

## ::constructor(objects...) : Object

Creates a new `Batman.Object` with properties from `objects`. If items in `objects` have the same keys, later values take precendence over earlier ones. Values are applied with `set`, so custom accessors are applied. The `Batman` namespace performs the same function.

    test 'Batman() function allows for handy creation of Batman.Objects', ->
      object = Batman(foo: 'bar')
      equal typeof object.get, 'function'

    test 'Batman.Object constructor function accepts multiple mixin arguments and later mixins take precedence.', ->
      song = Batman({length: 100, bpm: 120}, {bpm: 130})
      equal song.get('length'), 100
      equal song.get('bpm'), 130, "The property from the second object passed to the constructor overwrites that from the first."

## ::toJSON() : object

`toJSON` returns a vanilla JavaScript object representing this `Batman.Object`.

    test 'toJSON returns a vanilla JS object', ->
      object = Batman(foo: 'bar')
      deepEqual object.toJSON(), {foo: 'bar'}

## ::hashKey() : string

Returns a unique string identifying this `Batman.Object`.

## ::batchAccessorChanges(key, wrappedFunction)

Prevents accessor `key` from being recalculated while the `wrappedFunction` is called on the `Object`. After `wrappedFunction` is complete, the accessor will be recomputed. Returns the result of `wrappedFunction`.

## ::accessor([keys...], objectOrFunction)

`accessor` defines an accessor on one instance of an object instead of on all instances like the class level `@accessor`. See `@accessor` for the details surrounding accessors.

    test 'accessor can be called on an instance of Batman.Object to define an accessor just on that instance', ->
      class Post extends Batman.Object
        @accessor 'summary', -> @get('body').slice(0, 10) + "..."

      post = new Post(body: "Why Batman is Useful: A lengthy post on an important subject")
      equal post.get('summary'), "Why Batman..."
      post.accessor('longSummary', -> @get('body').slice(0, 20) + "...")  # "Instance level accessor defines accessors just for that instance"
      equal post.get('longSummary'), "Why Batman is Useful..."

    test 'defining an accessor on an instance does not affect the other instances', ->
      class Post extends Batman.Object

      post = new Post(body: "Why Batman is Useful: A lengthy post on an important subject")
      otherPost = new Post(body: "Why State Machines Are Useful: Another lengthy post")
      post.accessor 'longSummary', -> @get('body').slice(0, 20) + "..."
      equal post.get('longSummary'), "Why Batman is Useful..."
      equal otherPost.get('longSummary'), undefined

## ::mixin(objects...) : this

Mixes `objects` into the `Object` instance. Keys from `objects` are applied with `set`. If any of `objects` has an `initialize` function, it will be called with the prototype being mixed into.

    test 'mixin on an instance applies the keys from the mixed in object to the instance', ->
      class Snake extends Batman.Object

      snake = new Snake()
      snake.mixin {canSlither: true}, {canHiss: true}
      ok snake.get('canSlither')
      ok snake.get('canHiss')

# /api/Data Structures/Batman.Object

`Batman.Object` is the superclass for virtually all objects in a batman.js application. `Batman.Object` mixes in:

- `Batman.Observable` for `get`, `set`, `observe` and others
- `Batman.EventEmitter` for `on`, `off`, `fire` and others

See [`Batman.Object Accessors`](/docs/api/batman.object_accessors.html) for a full description of `@accessor`, which defines properties on `Batman.Object`s.

## @accessor([keys...], objectOrFunction)

If `keys` is empty, defines a new default accessor for instances of the object, otherwise defines a new accessor on instances of the `Object` for `keys`.

`objectOrFunction` may be:

- An object with `get`, `set`, and/or `unset` keys whose values are functions which implement those operations.
- A function which will be treated as the `get` key of the accessor object.

## @classAccessor([keys...], objectOrFunction)

Follows the pattern of `Bamtan.Object.accessor`, but defines the accessor on the class (constructor) instead of on instances of the object.

    test '@classAccessor defines an accessor on the class', ->
      class WayneManor extends Batman.Object
        @classAccessor 'address', -> "123 Wayne Dr."

      equal WayneManor.get('address'), "123 Wayne Dr."
      # Wayne Manor burned down...
      equal (new WayneManor(isRebuilt: true)).constructor.get('address'), "123 Wayne Dr."

## @mixin(objects...) : prototype

Mixes in `objects` to the `Object`'s prototype. Keys from `objects` are applied with `set`. If any of `objects` has an `initialize` function, it will be called with the prototype being mixed into.

_Note_: `@mixin`, similar to `@accessor`, applies to all instances of a class. If you need to mix in to the class itself, look at `classMixin`. `@mixin` is intended for use during the class definition of a `Batman.Object` subclass.

    test '@mixin extends the prototype of a Batman.Object subclass', ->
      FishBehaviour =
        canBreatheUnderwater: true
      MammalBehaviour =
        initialize: ->
          @set('isMammal', true)
        canBreatheAboveWater: true

      class Platypus extends Batman.Object
        @mixin FishBehaviour, MammalBehaviour

      platypus = new Platypus
      ok platypus.get('isMammal'), "the initialize function is called with the target prototype"
      ok platypus.get('canBreatheAboveWater')
      ok platypus.get('canBreatheUnderwater')

## @classMixin(objects...) : this

`@classMixin` mixes `objects` into the class (constructor) in the same way that `@mixin` mixes into the prototype.

    test '@classMixin extends the Batman.Object subclass', ->
      Singleton =
        initialze: (subject) ->
          subject.accessor 'instance', -> new subject

      class Highlander extends Batman.Object
        @classMixin Singleton

      instance = Highlander.get('instance')
      ok instance == Highlander.get('instance'), "There can only be one."

## @observeAll(key, callback : function) : prototype

`@observeAll` extends the `Batman.Object` implementation of `Batman.Observable` with the ability to observe all instances of the class (and subclasses). Observers attached with `@observeAll` function exactly as if they were attached to the object directly. Returns the prototype of the class.

_Note_: `@observeAll` is intended to be used during the class definition for a `Batman.Object` subclass, but it can be called after the class has been defined as a function on the class. It supports being called after instances of the class have been instantiated as well.

    test "@observeAll attaches handlers which get called upon change", ->
      results = []
      class Song extends Batman.Object
        @observeAll 'length', (newValue, oldValue) -> results.push newValue

      song = new Song({length: 340, bpm: 120})
      equal song.set('length', 200), 200
      deepEqual results[1], 200

    test "@observeAll can attach handlers after instance instantiation", ->
      results = []
      class Song extends Batman.Object

      song = new Song({length: 340, bpm: 120})
      equal song.set('length', 360), 360
      deepEqual results[0], undefined
      Song.observeAll 'length', (newValue, oldValue) -> results.push newValue
      equal song.set('length', 200), 200
      deepEqual results[0], 200

## @delegate(properties..., options)

Delegates `properties` to `options.to` by creating new accessors for `properties` which call `to.get(property)`. `options` must include a `to` Object.

## @singleton(singletonMethodName[="sharedInstance"])

Shorthand for [singleton classes](http://en.wikipedia.org/wiki/Singleton_pattern). Defines a class accessor `singletonMethodName` which returns the singleton instance.

## @wrapAccessor([keys...,] wrapperFunction: Function)

Defines a *wrap accessor* for the given keys. These accessors are intended to
extend an existing accessor or property by wrapping calls to `get`/`set`/`unset`.

`wrapperFunction` is called immediately, and should return an object with the
same format as an accessor definition. It is passed an object that represents
the original accessor being wrapped, called `core`.

Some trivial examples:

    test "@wrapAccessor can be used to extend get functionality", ->
      class Product extends Batman.Object
        @wrapAccessor 'title', (core) ->
          get: (key) -> 'Product ' + core.get.call(this, key) # Call the original get function.

      foo = new Product(title: 'Foo')
      equal foo.get('title'), 'Product Foo'

    test "@wrapAccessor can be used to extend set functionality", ->
      class Product extends Batman.Object
        @wrapAccessor 'title', (core) ->
          set: (key, value) ->
            core.set.call(this, key, value.toUpperCase()) # Call the original set function, with different arguments.

      foo = new Product(title: 'Product Foo')
      equal foo.get('title'), 'PRODUCT FOO'

Here's a real-world example of a fairly common use-case.
`Product` has a `handle`, which is the token used to identify the product in a
URL. If the user hasn't set a custom handle, then the handle should be generated
from the title. If they do set a custom handle, then changes to the title should
not affect the handle.

    test "@wrapAccessor makes custom shit woohoo", ->
      handleize = (value) -> value?.toLowerCase().replace(/\W+/g, '-')

      class Product extends Batman.Object
        @wrapAccessor 'handle', (core) ->
          get: -> core.get.apply(@, arguments) || handleize(@get('title'))

        @wrapAccessor 'title', (core) ->
          set: (key, value) ->
            if @get('handle') == handleize(@get('title'))
              @set('handle', handleize(value))

            core.set.call(this, key, value)

      foo = new Product(title: 'Product Foo!!')
      equal foo.get('handle'), 'product-foo-' # Handle is automatically set.

      foo.set('title', 'Product Bar')
      equal foo.get('handle'), 'product-bar' # Handle is automatically set again.

      foo.set('handle', 'custom-handle') # User defines a custom handle for this product...
      foo.set('title', 'Product Foo!!')
      equal foo.get('handle'), 'custom-handle' # so now it's not automatically set.

`@wrapAccessor` may be called with no keys to wrap *all* accessors.

## @wrapClassAccessor([keys...,] wrapperFunction: Function )

Like `@wrapAccessor`, but to wrap a class-level accessor.

## ::wrapAccessor([keys...,] wrapperFunction)

Like `@wrapAccessor`, but wraps an accessor on a single instance.

## ::constructor(objects...) : Object

Creates a new `Batman.Object` with properties from `objects`. If items in `objects` have the same keys, later values take precendence over earlier ones. Values are applied with `set`, so custom accessors are applied. The `Batman` namespace performs the same function.

    test 'Batman() function allows for handy creation of Batman.Objects', ->
      object = Batman(foo: 'bar')
      equal typeof object.get, 'function'

    test 'Batman.Object constructor function accepts multiple mixin arguments and later mixins take precedence.', ->
      song = Batman({length: 100, bpm: 120}, {bpm: 130})
      equal song.get('length'), 100
      equal song.get('bpm'), 130, "The property from the second object passed to the constructor overwrites that from the first."

## ::toJSON() : object

`toJSON` returns a vanilla JavaScript object representing this `Batman.Object`.

    test 'toJSON returns a vanilla JS object', ->
      object = Batman(foo: 'bar')
      deepEqual object.toJSON(), {foo: 'bar'}

## ::hashKey() : string

Returns a unique string identifying this `Batman.Object`.

## ::batchAccessorChanges(key, wrappedFunction)

Prevents accessor `key` from being recalculated while the `wrappedFunction` is called on the `Object`. After `wrappedFunction` is complete, the accessor will be recomputed. Returns the result of `wrappedFunction`.

## ::accessor([keys...], objectOrFunction)

`accessor` defines an accessor on one instance of an object instead of on all instances like the class level `@accessor`. See `@accessor` for the details surrounding accessors.

    test 'accessor can be called on an instance of Batman.Object to define an accessor just on that instance', ->
      class Post extends Batman.Object
        @accessor 'summary', -> @get('body').slice(0, 10) + "..."

      post = new Post(body: "Why Batman is Useful: A lengthy post on an important subject")
      equal post.get('summary'), "Why Batman..."
      post.accessor('longSummary', -> @get('body').slice(0, 20) + "...")  # "Instance level accessor defines accessors just for that instance"
      equal post.get('longSummary'), "Why Batman is Useful..."

    test 'defining an accessor on an instance does not affect the other instances', ->
      class Post extends Batman.Object

      post = new Post(body: "Why Batman is Useful: A lengthy post on an important subject")
      otherPost = new Post(body: "Why State Machines Are Useful: Another lengthy post")
      post.accessor 'longSummary', -> @get('body').slice(0, 20) + "..."
      equal post.get('longSummary'), "Why Batman is Useful..."
      equal otherPost.get('longSummary'), undefined

## ::mixin(objects...) : this

Mixes `objects` into the `Object` instance. Keys from `objects` are applied with `set`. If any of `objects` has an `initialize` function, it will be called with the prototype being mixed into.

    test 'mixin on an instance applies the keys from the mixed in object to the instance', ->
      class Snake extends Batman.Object

      snake = new Snake()
      snake.mixin {canSlither: true}, {canHiss: true}
      ok snake.get('canSlither')
      ok snake.get('canHiss')


Add docs about using custom URLs

Add docs about using custom URLs


Refactor to use new db schema

Refactor to use new db schema

    PostgresRenderer = require './postgres_renderer'

    DB = undefined

    class PostgresGround extends PostgresRenderer

      delegates: [
        'ground'
        'stairs_up'
      ]

      $register_db_instance: (done) ->
        DB = @_postgres()
        done()

      render: (path, grid_name, done, exception) ->
        grid_save_query = @sql_bricks_postgres
          .insert 'grid', name: grid_name
          .returning 'id'
          .toParams()

        DB.one grid_save_query.text, grid_save_query.values
          .then (g) =>
            @async.each path, (p, next) =>
              block_save_query = @sql_bricks_postgres
                .insert 'block',
                  grid:       g.id
                  size:       "(#{p.width.actual}, #{p.height.actual})"
                  properties: p.props
                  direction:  p.direction
                .returning 'id'
                .toParams()

              DB.one block_save_query.text, block_save_query.values
                .then (b) =>
                  @async.each p.landscape.nodes, (node, nxt) =>
                    node_save_query = @sql_bricks_postgres
                      .insert 'node',
                        block:    b.id
                        kind:     node.type
                        size:     "(#{node.width}, #{node.height})"
                        location: "(#{node.x}, #{node.y})"
                      .returning 'id'
                      .toParams()

                    DB.one node_save_query.text, node_save_query.values
                      .then (n) =>
                        faces  = @[node.type] node
                        params =
                          node:        n.id
                          left_face:   faces.left
                          top_face:    faces.top
                          right_face:  faces.right
                          bottom_face: faces.bottom
                          front_face:  faces.front
                          back_face:   faces.back

                        geom_query = @sql_bricks_postgres
                          .insert 'geometry', params
                          .toParams()

                        DB.none geom_query.text, geom_query.values
                          .then => nxt()
                          .catch exception nxt
                      .catch exception nxt
                  , => next()
                .catch exception next
            , => done()

    module.exports = PostgresGround

    PostgresRenderer = require './postgres_renderer'

    class PostgresGround extends PostgresRenderer

      args: [ 'wall' ]

      render: (path, _, grid_name, done, exception) ->
        grid_query = @sql_bricks_postgres
          .select 'id'
          .from   'grid'
          .where  name: grid_name
          .limit  1
          .toParams()

        @_postgres().one grid_query.text, grid_query.values
          .then (grid) =>
            piece_query = @sql_bricks_postgres
              .select 'id'
              .from   'piece'
              .where  mode: 'GROUND'
              .limit  1
              .toParams()

            @_postgres().one piece_query.text, piece_query.values
              .then (piece) =>
                @async.each path, (item, all_inserted) =>
                  block_query = @sql_bricks_postgres
                    .select 'id'
                    .from   'block'
                    .where
                      grid:  grid.id
                      index: path.indexOf item
                    .limit  1
                    .toParams()

                  @_postgres().one block_query.text, block_query.values
                    .then (block) =>
                      @async.each item.ground, (ground, inserted) =>
                        properties =
                          x:      item.ground.indexOf ground
                          y:      @wall.segments - ground.thickness
                          block:  block.id
                          piece:  piece.id
                          volume: x: 1, y: ground.thickness, z: 1

                        add = @sql_bricks_postgres
                          .insert 'point', properties
                          .toParams()

                        @_postgres().none add.text, add.values
                          .catch exception
                          .then  inserted
                      , all_inserted
                    .catch exception
                , done
              .catch exception

    module.exports = PostgresGround


Singularize cats

Singularize cats

# Batman.View

For a general explanation of `Batman.View`s and how they work, see [the
guide](/docs/views.html).

## ::constructor(options = {})

A `View` is a `Batman.Object`, so any options you pass are mixed in. Use this
to set `html`, `node`, `superview`, `parentNode` and/or your custom data.

    test 'constructor mixes in options', ->
      view = new Batman.View(animal: 'cat')
      equal 'cat', view.get('animal')

## ::lookupKeypath(keypath) : Object

Traverses up the view tree searching for the specified keypath, and returns the
result. This is equivalent to performing a `Batman.get` for each view above
`this` in the tree, until a defined result is returned. The path it takes is as
follows:

current view → chain of superviews → layout view → active controller → app →
window

If there is no match, `undefined` is returned. However if used in an accessor
or binding, the entire path to the root will be registered as a potential
source of the keypath. Consequently, if the keypath is later set on any part of
the chain, the data will be correctly bound.

`lookupKeypath` is the function invoked to locate data when evaluating a
binding.

    test 'lookupKeypath returns the value if defined on the view', ->
      view = new Batman.View(animal: 'cat')
      equal 'cat', view.lookupKeypath('animal')

    test 'lookupKeypath returns the value if defined on an ancestor', ->
      superview = new Batman.View(animal: 'cat')
      subview = new Batman.View(superview: superview)
      equal 'cat', subview.lookupKeypath('animal')

## ::setKeypath(keypath, value) : Object

Traverses the View tree searching for the specified keypath, and sets the value
on the nearest ancestor which defines it. If no ancestor view defines the given
keypath, it will be set on the nearest ancestor which is not a
backing view.

`setKeypath` is the function invoked to set data when using an input binding.

    test 'setKeypath sets the value if defined on the view', ->
      view = new Batman.View(animal: 'dog')

      view.setKeypath('animal', cat)
      equal 'cat', view.get('animal')

    test 'setKeypath sets the value if defined on an ancestor', ->
      superview = new Batman.View(animal: 'dog')
      subview = new Batman.View(superview: superview)

      subview.setKeypath('animal', cat)
      equal 'cat', superview.get('animal')

    test 'setKeypath sets the value on the nearest non-backing view when not defined anywhere', ->
      superview = new Batman.View()
      view = new Batman.View(superview: superview)
      backingView = new Batman.BackingView(superview: view)

      backingView.setKeypath('animal', cat)
      equal 'cat', view.get('animal')

## ::%node : Node

A reference to the DOM node that this view encapsulates. The entire tree
beneath this node is also the responsibility of this view and/or its subviews.

Accessing `node` will load and parse the template on demand if it isn't already
loaded.

    test 'node parses the template', ->
      view = new Batman.View(html: '
cat
')

      node = view.get('node')
      equal 'cat', node.firstChild.innerHTML

    test 'node parses bindings too', ->
      view = new Batman.View(html: '

', animal: 'cat')

      node = view.get('node')
      equal 'cat', node.firstChild.innerHTML

## ::%html : String

The HTML source for the view's template. Setting this will parse the template
and build bindings automatically, but it will not be inserted into the DOM
until the view is added to a superview.

If you don't explicitly set `html` but you do set `source`, then getting `html`
will automatically fetch the template source from the local template store.

## ::.superview : Batman.View

A reference to the current superview (the direct ancestor in the tree). This is
used for traversing the tree when searching for data, as in
`View::lookupKeypath`.

## ::.subviews : Batman.Set

The set of direct children of a `View`. To manipulate the view tree, you should
operate directly on this set — batman.js will automatically keep the DOM in
sync with the logical tree.

## ::subviews.add(view)

Adding to a view's subview set will automatically update the tree, and parse
the template and bindings. If the superview is already in the DOM, this will
insert the current view's node into the DOM.

## ::subviews.remove(view)

Removing from a view's subview set will automatically remove the subview from
the DOM.

## ::removeFromSuperview()

Removes this view from its parent, without killing it.

## ::die()

Kills this view, which renders it to forever unusable. This has the
following implications:

- The view is removed from its superview
- The view's node is removed from the DOM
- The view's bindings are destroyed
- The view's current subviews are killed

    test 'die kills the view', ->
      superview = new Batman.View()
      view = new Batman.View(superview: superview)

      view.die()
      equal true, view.isDead
      equal 0, superview.subviews.length

## ::.isDead : boolean

True if the view has been killed, false otherwise.

## ::destroySubviews()

Kills every subview of this view.

## ::propagateToSubviews(eventOrKey : string, value)

If value is defined, set `eventOrKey` to `value` on the entire subtree.
Otherwise, fire `eventOrKey` on the entire subtree.

## @viewForNode(node, climbTree = true) : Batman.View

Finds the view acting as the current context for a node — i.e. perform the
reverse mapping of the view tree to the DOM. If you pass `false` for
`climbTree`, it won't traverse up the DOM, and will return `undefined` unless
the node is the view's root.

# Batman.View

For a general explanation of `Batman.View`s and how they work, see [the
guide](/docs/views.html).

## ::constructor(options = {})

A `View` is a `Batman.Object`, so any options you pass are mixed in. Use this
to set `html`, `node`, `superview`, `parentNode` and/or your custom data.

    test 'constructor can be called without arguments', ->
      set = new Batman.Set
      deepEqual set.toArray(), []

## ::lookupKeypath(keypath) : Object

Traverses up the view tree searching for the specified keypath, and returns the
result. This is equivalent to performing a `Batman.get` for each view above
`this` in the tree, until a defined result is returned. The path it takes is as
follows:

current view → chain of superviews → layout view → active controller → app →
window

If there is no match, `undefined` is returned. However if used in an accessor
or binding, the entire path to the root will be registered as a potential
source of the keypath. Consequently, if the keypath is later set on any part of
the chain, the data will be correctly bound.

`lookupKeypath` is the function invoked to locate data when evaluating a
binding.

    test 'lookupKeypath returns the value if defined on the view', ->
      view = new Batman.View(animal: 'cats')
      equal 'cats', view.lookupKeypath('animal')

    test 'lookupKeypath returns the value if defined on an ancestor', ->
      superview = new Batman.View(animal: 'cats')
      subview = new Batman.View(superview: superview)
      equal 'cats', subview.lookupKeypath('animal')

## ::setKeypath(keypath, value) : Object

Traverses the View tree searching for the specified keypath, and sets the value
on the nearest ancestor which defines it. If no ancestor view defines the given
keypath, it will be set on the nearest ancestor which is not a
backing view.

`setKeypath` is the function invoked to set data when using an input binding.

    test 'setKeypath sets the value if defined on the view', ->
      view = new Batman.View(animal: 'dogs')

      view.setKeypath('animal', cats)
      equal 'cats', view.get('animal')

    test 'setKeypath sets the value if defined on an ancestor', ->
      superview = new Batman.View(animal: 'dogs')
      subview = new Batman.View(superview: superview)

      subview.setKeypath('animal', cats)
      equal 'cats', superview.get('animal')

    test 'setKeypath sets the value on the nearest non-backing view when not defined anywhere', ->
      superview = new Batman.View()
      view = new Batman.View(superview: superview)
      backingView = new Batman.BackingView(superview: view)

      backingView.setKeypath('animal', cats)
      equal 'cats', view.get('animal')

## ::%node : Node

A reference to the DOM node that this view encapsulates. The entire tree
beneath this node is also the responsibility of this view and/or its subviews.

Accessing `node` will load and parse the template on demand if it isn't already
loaded.

    test 'node parses the template', ->
      view = new Batman.View(html: '
cat
')

      node = view.get('node')
      equal 'cat', node.firstChild.innerHTML

    test 'node parses bindings too', ->
      view = new Batman.View(html: '

', animal: 'cat')

      node = view.get('node')
      equal 'cat', node.firstChild.innerHTML

## ::%html : String

The HTML source for the view's template. Setting this will parse the template
and build bindings automatically, but it will not be inserted into the DOM
until the view is added to a superview.

If you don't explicitly set `html` but you do set `source`, then getting `html`
will automatically fetch the template source from the local template store.

## ::.superview : Batman.View

A reference to the current superview (the direct ancestor in the tree). This is
used for traversing the tree when searching for data, as in
`View::lookupKeypath`.

## ::.subviews : Batman.Set

The set of direct children of a `View`. To manipulate the view tree, you should
operate directly on this set — batman.js will automatically keep the DOM in
sync with the logical tree.

## ::subviews.add(view)

Adding to a view's subview set will automatically update the tree, and parse
the template and bindings. If the superview is already in the DOM, this will
insert the current view's node into the DOM.

## ::subviews.remove(view)

Removing from a view's subview set will automatically remove the subview from
the DOM.

## ::removeFromSuperview()

Removes this view from its parent, without killing it.

## ::die()

Kills this view, which renders it to forever unusable. This has the
following implications:

- The view is removed from its superview
- The view's node is removed from the DOM
- The view's bindings are destroyed
- The view's current subviews are killed

    test 'die kills the view', ->
      superview = new Batman.View()
      view = new Batman.View(superview: superview)

      view.die()
      equal true, view.isDead
      equal 0, superview.subviews.length

## ::.isDead : boolean

True if the view has been killed, false otherwise.

## ::destroySubviews()

Kills every subview of this view.

## ::propagateToSubviews(eventOrKey : string, value)

If value is defined, set `eventOrKey` to `value` on the entire subtree.
Otherwise, fire `eventOrKey` on the entire subtree.

## @viewForNode(node, climbTree = true) : Batman.View

Finds the view acting as the current context for a node — i.e. perform the
reverse mapping of the view tree to the DOM. If you pass `false` for
`climbTree`, it won't traverse up the DOM, and will return `undefined` unless
the node is the view's root.


Use Madul.DUMMY to load render_pipeline

Use Madul.DUMMY to load render_pipeline

    `#! /usr/bin/env node
    `

    Madul = require 'madul'

    if process.env.SKYLL_MADUL_LOGGING == 'true'
      require 'magnus'

    Skyll = require './index'
    args  = require './arguments'
    uuid  = require 'node-uuid'
    fs    = require 'fs'
    path  = require 'path'

    EXTRACT = [
      'rows'
      'columns'
      'width'
      'height'
      'multiplier'
      'pipeline'
      'block'
      'ground'
      'step_count'
      'wall'
    ]

    new Skyll()
      .initialize args
      .then (mod) ->
        levels = [ ]

        if args._?.length > 0
          levels = levels.concat argv._
        else if args.l?
          for level in [0...argv.l]
            levels.push uuid.v4()
        else if Array.isArray args.levels
          for level in args.levels
            levels.push level
        else if args.levels? == false
          levels.push new Date().toString()

        if args.delegates?
          location = args.delegates
        else
          location = path.join process.cwd(), 'skyll.delegates.js'

        fs.stat location, (err) ->
          if err?
            mod.warn 'file-not-found', location
          else
            delegates = require location
            next      = 0
            input     = { }
            pipe      = [ ]

            for own key, val of args
              input[key] = val if EXTRACT.includes key

            Madul.DUMMY pipe, (dum) ->
              dum.render_pipeline = [ ]

              for p in input.pipeline
                if Array.isArray p
                  new_pipeline = for q in p
                    dum[Madul.PARSE_SPEC(q).ref]

                  dum.render_pipeline.push new_pipeline
                else
                  dum.render_pipeline.push dum[Madul.PARSE_SPEC(p).ref]

              args = { }
              name = new Date().toString()

              for own key, val of input
                args[key] = val if EXTRACT.includes key

              render = (level) ->
                mod.craft level, input, dum.render_pipeline, delegates
                  .then -> render levels[next] if ++next < levels.length

              render levels[next]

    `#! /usr/bin/env node
    `

    if process.env.SKYLL_MADUL_LOGGING == 'true'
      require 'magnus'

    Skyll = require './index'
    args  = require './arguments'
    uuid  = require 'node-uuid'
    fs    = require 'fs'
    path  = require 'path'

    EXTRACT = [
      'rows'
      'columns'
      'width'
      'height'
      'multiplier'
      'pipeline'
      'block'
      'ground'
      'step_count'
      'wall'
    ]

    new Skyll()
      .initialize args
      .then (mod) ->
        levels = [ ]

        if args._?.length > 0
          levels = levels.concat argv._
        else if args.l?
          for level in [0...argv.l]
            levels.push uuid.v4()
        else if Array.isArray args.levels
          for level in args.levels
            levels.push level
        else if args.levels? == false
          levels.push new Date().toString()

        if args.delegates?
          location = args.delegates
        else
          location = path.join process.cwd(), 'skyll.delegates.js'

        fs.stat location, (err) ->
          if err?
            mod.warn 'file-not-found', location
          else
            delegates = require location
            next      = 0
            input     = { }

            for own key, val of args
              input[key] = val if EXTRACT.includes key

            mod.setup_rendering_pipeline args.pipeline
              .then ->
                render = (level) ->
                  mod.craft level, input, delegates
                    .then -> render levels[next] if ++next < levels.length

                render levels[next]


Replaced _parse_handle method with spec helpers

    q     = require 'q'
    fs    = require 'fs'
    async = require 'async'
    uuid  = require 'uuid-1345'

    microtime = require 'microtime'

    EventEmitter2 = require('eventemitter2').EventEmitter2
    emitter       = new EventEmitter2 wildcard: true

    available   = { }
    initialized = { }
    listeners   = { }

    code_root = process.env.SEARCH_ROOT || 'dist'

    underscore = (value) -> value.replace /\W+/g, '_'
    strip      = (name)  -> name.toLowerCase().replace /\W+/g, ''

    SEARCH_ROOTS  = { }
    WRAPPED       = { }
    _INITIALIZERS = { }
    HYDRATED      = { }

    HYRDATION_LISTENERS = { }

    INITIALIZERS = (cls, method) ->
      _INITIALIZERS[cls] = [ ] unless _INITIALIZERS[cls]?

      _INITIALIZERS[cls].push fn: method, called: false

    WRAP = (cls, method) ->
      unless WRAPPED[cls]?
        WRAPPED[cls] = [
          'constructor'
          'initialize'
          'details'
        ]

      WRAPPED[cls].indexOf(method) < 0

    class Madul

      details: =>
        name  = @.__proto__.constructor.name
        props = for own key, val of @.__proto__
          if key != 'constructor' &&
             key != 'details'     &&
             key != 'initialize'  && ((
               key[0]            == '_' &&
               @.__proto__[key]? == false
             ) || key[0] != '_')

            if typeof val == 'function'
              value = val.constructor.name
            else if Array.isArray val
              value = for v in val
                if typeof v == 'function'
                  v.constructor.name
                else if typeof v == 'object'
                  v.constructor.name
                else
                  v
              value = value.join ','
            else if typeof val == 'object'
              value = val.constructor.name
            else
              value = val

            "#{key} => #{value}"

        "\n  #{name}\n    #{props.filter((e) -> e?).join '\n    '}"

      @LISTEN: (event, callback) => emitter.on event, callback

      @FIRE: (event, args) => emitter.emit event, args

      @SEARCH_ROOT: (mod, path) =>
        Madul.FIRE '$.Madul.search_root.register', "#{mod}": path

        SEARCH_ROOTS[mod] = path.substring 0, path.lastIndexOf '/'

      @PARSE_SPEC: (value) =>
        tokens = value.split '='

        if tokens.length == 2
          initer = tokens[1].trim()
          t      = tokens[0].split '->'

          if t[0].indexOf('#') > -1
            r = t[0].split '#'

            root = r[0].trim()
            t[0] = r[1]

          if t.length == 2
            n = t[0].trim()

            if n[0] == '.'
              local = true
              name  = n.substring 1, n.length
            else
              local = false
              name  = n

            alias = t[1].trim()
          else if t.length == 1
            n = t[0].trim()

            if n[0] == '.'
              local = true
              name  = alias = n.substring 1, n.length
            else
              local = false
              name  = alias = n
          else
            return Madul.FIRE '!.Madul.dependency_spec.alias.invalid', tokens[1]

          toks = initer.split ':'

          if toks.length == 2
            initer = toks[0].trim()
            pres   = toks[1].split(',').map (p) => p.trim()
          else if toks.length == 1
            initer = toks[0].trim()
          else
            return Madul.FIRE '!.Madul.dependency_spec.initializer.invalid', tokens[1]

        else if tokens.length == 1
          t = tokens[0].split '->'

          if t[0].indexOf('#') > -1
            r = t[0].split '#'

            root = r[0].trim()
            t[0] = r[1]

          if t.length == 2
            n = t[0].trim()

            if n[0] == '.'
              local = true
              name  = n.substring 1, n.length
            else
              local = false
              name  = n

            alias = t[1].trim()
          else if t.length == 1
            n = t[0].trim()

            if n[0] == '.'
              local = true
              name  = alias = n.substring 1, n.length
            else
              local = false
              name  = alias = n
          else
            return Madul.FIRE '!.Madul.dependency_spec.alias.invalid', tokens[1]

        else
          return Madul.FIRE '!.Madul.dependency_spec.invalid', d

        { ref: alias || name, alias, name, root, initer, pres, local }

      @BUILD_SPEC: ({ search_root, name, alias, initializer, prerequisites }) =>
        unless name?
          return Madul.FIRE '!.Madul.dependency_spec.name-required', arguments[0]

        if prerequisites? && initializer? == false
          return Madul.FIRE '!.Madul.dependency_spec.prerequisites-require-initializer', arguments[0]

        "#{if search_root?   then "#{search_root}#"            else ''}\
         #{name}\
         #{if alias?         then " -> #{alias}"               else ''}\
         #{if initializer?   then " = #{initializer}"          else ''}\
         #{if prerequisites? then ":#{prerequisites.join ','}" else ''}\
        "

      listen: (event, callback) ->
        Madul.LISTEN "*.#{@constructor.name}.#{event}", callback

      fire: (event, args) ->
        Madul.FIRE "@.#{@constructor.name}.#{event}", args

      warn: (event, details) ->
        Madul.FIRE "!.#{@constructor.name}.#{event}", details

      _report: (name, method, state, id, args) =>
        Madul.FIRE "@.#{name}.#{method}.#{state}",
          uuid:      id
          args:      args
          timestamp: microtime.now()

      _respond: (proto, method, id, deferred) =>
        (state, data) =>
          process.nextTick =>
            deferred[state] data

            proto._report proto.constructor.name, method, state, id, data

      _prep_invocation: (proto, method, input, def) =>
        id  = uuid.v4fast()
        res = proto._respond proto, method, id, def

        if Array.isArray input
          input.push (out) => res 'resolve', out
          input.push (err) => res 'reject',  err
          input.push (out) => res 'notify',  out
        else if typeof input == 'object'
          input.done   = (out) => res 'resolve', out
          input.fail   = (err) => res 'reject',  err
          input.update = (out) => res 'notify',  out

          input = [ input ]
        else
          msg = "input to #{proto.constructor.name}.#{method} must be an Array of Object"
          @warn 'input.invalid', msg
          throw new Error msg

        proto._report proto.constructor.name, method, 'invoke', id, input

        input

      _do_wrap: (proto, method) =>
        if method != 'fire' && method != 'warn' && method != 'listen'
          Madul.FIRE "$.#{proto.constructor.name}.#{method}.wrap"

          if typeof proto[method] == 'function'
            proto["_#{method}"] = proto[method]

            proto[method] = =>
              def  = q.defer()
              args = if arguments[0]? then Array.prototype.slice.call arguments else [ ]

              proto["_#{method}"].apply @, proto._prep_invocation proto, method, args, def

              def.promise
          else if typeof proto[method] == 'object'

            if Array.isArray proto[method].validate
              args_format = 'ARRAY'
              decs        = for val in proto[method].validate
                @_parse_handle(val).ref

              proto[method].validate = decs
            else if typeof proto[method].validate == 'object'
              args_format = 'OBJECT'
              decs        = for own key, val of proto[method].validate
                { ref } = @_parse_handle val
                proto[method].validate[key] = ref
                ref
            else if typeof proto[method].validate == 'string'
              args_format = 'ARRAY'
              decs        = [ @_parse_handle(proto[method].validate).ref ]
            else if typeof proto[method].validate != 'undefined'
              @warn 'meta.invalid', validate: 'must be a String, Object, or Array'
              return
            else
              args_format = 'ARRAY'
              decs        = [ ]

            decs = decs.concat(proto[method].before.map (b, i) =>
              { ref } = @_parse_handle b
              proto[method].before[i] = ref
              ref
            ) if proto[method].before?

            decs = decs.concat(proto[method].after.map (a, i) =>
              { ref } = @_parse_handle a
              proto[method].after[i] = ref
              ref
            ) if proto[method].after?

            Madul.FIRE '$.Madul.decorators.hydrate', decs

            @_do_hydrate proto, decs, =>
              proto["_#{method}"] = proto[method]

              proto[method] = =>
                def = q.defer()
                me  = proto["_#{method}"]

                if args_format == 'ARRAY'
                  args = Array.prototype.slice.call arguments

                  if me.validate?
                    validators = for val, i in me.validate
                      { ref } = @_parse_handle val
                      Madul.FIRE '$.Madul.validator.execute', "#{ref}": args[i]
                      proto[ref].EXECUTE args[i]
                else if args_format == 'OBJECT'
                  args = arguments[0]

                  if me.validate?
                    validators = for own key, val of me.validate
                      { ref } = @_parse_handle val
                      Madul.FIRE '$.Madul.validator.execute', "#{ref}": args[key]
                      proto[ref].EXECUTE args[key]
                else
                  @warn 'cannot-continue', 'No arg format specified'

                  return def.reject 'No arg format specified'

                me.before = [ ] unless me.before?
                me.after  = [ ] unless me.after?

                q.all validators
                .then =>
                  q.all me.before.map (b) =>
                    Madul.FIRE '$.Madul.before_filter.execute', "#{b}": args
                    proto[b].before args
                .then =>
                  me.behavior.apply @, @_prep_invocation proto, method, args, def
                .then (result) =>
                  if me.after.length > 0
                    q.all me.after.map (b) =>
                      Madul.FIRE '$.Madul.after_filter.execute', "#{b}": result
                      b.after result
                  else
                    d = q.defer()

                    process.nextTick => d.resolve result

                    d.promise
                .then  (out) => def.resolve out
                .catch (err) => def.reject  err

                def.promise
          else
            @warn 'cannot-wrap', method

          WRAPPED[proto.constructor.name].push method

      _wrap_methods: (proto, callback) =>
        name    = proto.constructor.name
        to_wrap = [ ]

        while proto? && Object.keys(proto).length > 0 && WRAPPED[name]? == false
          to_wrap.push { proto, name, methods: [ ] }

          for own prop, body of proto
            if prop[0]                  != '_'         &&
               typeof proto["_#{prop}"] == 'undefined' &&
               WRAP(name, prop)         == true

              continue if proto.deps? && proto.deps.indexOf(prop.replace(/_/g, '-')) > -1

              if typeof body == 'function' || typeof body?.behavior == 'function'
                to_wrap[to_wrap.length - 1].methods.push prop

          proto = proto.__proto__
          name  = proto.constructor.name

        async.each to_wrap.reverse(), (wrap, completed) =>
          async.each wrap.methods, (method, next) =>
            wrap.proto._do_wrap wrap.proto, method

            INITIALIZERS wrap.name, method if method[0] == '$'

            next()
          , => @_call_initializers_for wrap.proto, wrap.name, completed
        , callback

      _make_available: (name, mod) =>
        Madul.FIRE "$.#{name}.available"

        available[strip name] = mod

      _hydrate_deps: (proto, done) =>
        protos = [ proto ]

        if proto.__proto__?
          while proto.__proto__? && Object.keys(proto.__proto__).length > 0
            protos.push proto = proto.__proto__

        async.each protos.reverse(), (p, next) =>
          name = p.constructor.name

          if p.hasOwnProperty 'deps'
            if HYDRATED[name] == undefined
              HYDRATED[name]            = false
              HYRDATION_LISTENERS[name] = [ next ]

              p._do_hydrate p, p.deps, =>
                HYDRATED[name] = true

                for listener in HYRDATION_LISTENERS[name]
                  listener()
            else if HYDRATED[name] == false
              HYRDATION_LISTENERS[name].push next
            else if HYDRATED[name] == true
              next()
          else
            next()
        , done

      _init_if_madul: (path, callback) =>
        mod      = require path
        proto    = mod
        is_madul = false

        while proto
          is_madul = true if proto.name == 'Madul'
          if is_madul                            == false      &&
             proto.constructor.name              != 'Object'   &&
             typeof proto                        == 'function' &&
             typeof proto.__super__?.constructor == 'function'
            proto = proto.__super__.constructor
          else
            proto = undefined

        if is_madul
          new mod()
            .initialize()
            .then callback
        else
          callback mod

      _load: (me, name, path, loaded) =>
        me._init_if_madul path, (mod) =>
          me._make_available name, mod
          loaded mod

      _check: (me, path, dep, ref, finished) =>
        fs.readdir path, (err, files) =>
          if err?
            me.warn 'file-not-found', err

            done type: 'ERROR', info: err
          else
            async.each files, (f, next) =>
              depth = "#{path}/#{f}"

              fs.stat depth, (e, s) =>
                if s.isDirectory() && f[0] != '.'
                  me._check me, depth, dep, ref, next
                else if s.isFile() && f.substring(0, f.length - 3) == dep
                  me._load me, ref, depth, (mod) => me._do_add me, mod, ref, next
                else
                  next()
            , finished

      _do_add: (me, mod, ref, next) =>
        Madul.FIRE "$.#{me.constructor.name}.dependency.register", ref

        me[underscore ref] = mod

        next()

      _add: (me, ref, path, next) =>
        me._init_if_madul path, (mod) =>
          me._make_available ref, mod
          me._do_add me, mod, ref, next

      _do_hydrate: (proto, deps, hydration_complete) =>
        initers = [ ]

        async.each deps, (d, next) =>
          { ref, alias, name, root, initer, pres } = @_parse_handle d

          if pres?
            insert_at = for p in pres
              index_for = (sibling) => sibling.alias == p.alias

              initers.find index_for

            insert_at.sort()

            insert_at = if insert_at.length == 0 then 0 else insert_at[insert_at.length - 1]

            initers.splice insert_at, 0, alias: alias, execute: initer

          if proto[underscore ref]? == false
            if available[strip ref]? == true
              proto._do_add proto, available[strip ref], ref, next
            else
              try
                proto._add proto, ref, name, next
              catch e
                if root?
                  Madul.FIRE '$.Madul.search_root.load', { name, alias, root }

                  proto._check proto, root, name, ref, next
                else
                  cwd = process.cwd()
                  pkg = "#{cwd}/node_modules/#{name}/package.json"

                  fs.stat pkg, (err, stat) =>
                    if stat?.isFile()
                      fs.readFile pkg, 'utf8', (err, data) =>
                        json = JSON.parse data
                        main = json.main || json._main || 'index.js'
                        path = "#{cwd}/node_modules/#{name}/#{main}"

                        proto._add proto, ref, path, next
                    else
                      proto._check proto, "#{cwd}/#{code_root}", name, ref, next
          else
            next()
        , =>
          async.eachSeries initers, (initer, next) =>
            proto[initer.execute].apply(@).then next
          , hydration_complete

      _finish_up: (proto, args) =>
        name = proto.constructor.name

        if listeners[name]?
          async.each listeners[name], (listener, next) =>
            listener @
            next()
          , => @_register_initialized name
        else
          @_register_initialized name

      _register_initialized: (name) =>
        @_make_available name, @

        initialized[name] = true

        Madul.FIRE "$.#{name}.initialized"

      _call_initializers_for: (proto, name, callback) =>
        if _INITIALIZERS[name]?
          async.each _INITIALIZERS[name], (initializer, next) =>
            if initializer.called == false
              proto[initializer.fn].apply @
                .then =>
                  initializer.called = true
                  next()
            else
              next()
          , callback
        else
          callback()

      initialize: =>
        deferred = q.defer()
        proto    = @.__proto__
        name     = proto.constructor.name

        Madul.FIRE "$.#{name}.request_instance"

        if initialized[name] == undefined
          Madul.FIRE "$.#{name}.initialize"

          initialized[name] = false
          listeners[name]   = [ deferred.resolve ]

          @_hydrate_deps proto, => @_wrap_methods proto, => @_finish_up proto
        else if initialized[name] == false
          listeners[name].push deferred.resolve
        else if initialized[name] == true
          process.nextTick => deferred.resolve available[strip name]

        deferred.promise

    module.exports = Madul

    q     = require 'q'
    fs    = require 'fs'
    async = require 'async'
    uuid  = require 'uuid-1345'

    microtime = require 'microtime'

    EventEmitter2 = require('eventemitter2').EventEmitter2
    emitter       = new EventEmitter2 wildcard: true

    available   = { }
    initialized = { }
    listeners   = { }

    code_root = process.env.SEARCH_ROOT || 'dist'

    underscore = (value) -> value.replace /\W+/g, '_'
    strip      = (name)  -> name.toLowerCase().replace /\W+/g, ''

    SEARCH_ROOTS  = { }
    WRAPPED       = { }
    _INITIALIZERS = { }
    HYDRATED      = { }

    HYRDATION_LISTENERS = { }

    INITIALIZERS = (cls, method) ->
      _INITIALIZERS[cls] = [ ] unless _INITIALIZERS[cls]?

      _INITIALIZERS[cls].push fn: method, called: false

    WRAP = (cls, method) ->
      unless WRAPPED[cls]?
        WRAPPED[cls] = [
          'constructor'
          'initialize'
          'details'
        ]

      WRAPPED[cls].indexOf(method) < 0

    class Madul

      details: =>
        name  = @.__proto__.constructor.name
        props = for own key, val of @.__proto__
          if key != 'constructor' &&
             key != 'details'     &&
             key != 'initialize'  && ((
               key[0]            == '_' &&
               @.__proto__[key]? == false
             ) || key[0] != '_')

            if typeof val == 'function'
              value = val.constructor.name
            else if Array.isArray val
              value = for v in val
                if typeof v == 'function'
                  v.constructor.name
                else if typeof v == 'object'
                  v.constructor.name
                else
                  v
              value = value.join ','
            else if typeof val == 'object'
              value = val.constructor.name
            else
              value = val

            "#{key} => #{value}"

        "\n  #{name}\n    #{props.filter((e) -> e?).join '\n    '}"

      @LISTEN: (event, callback) => emitter.on event, callback

      @FIRE: (event, args) => emitter.emit event, args

      @SEARCH_ROOT: (mod, path) =>
        Madul.FIRE '$.Madul.search_root.register', "#{mod}": path

        SEARCH_ROOTS[mod] = path.substring 0, path.lastIndexOf '/'

      listen: (event, callback) ->
        Madul.LISTEN "*.#{@constructor.name}.#{event}", callback

      fire: (event, args) ->
        Madul.FIRE "@.#{@constructor.name}.#{event}", args

      warn: (event, details) ->
        Madul.FIRE "!.#{@constructor.name}.#{event}", details

      _report: (name, method, state, id, args) =>
        Madul.FIRE "@.#{name}.#{method}.#{state}",
          uuid:      id
          args:      args
          timestamp: microtime.now()

      _respond: (proto, method, id, deferred) =>
        (state, data) =>
          process.nextTick =>
            deferred[state] data

            proto._report proto.constructor.name, method, state, id, data

      _prep_invocation: (proto, method, input, def) =>
        id  = uuid.v4fast()
        res = proto._respond proto, method, id, def

        if Array.isArray input
          input.push (out) => res 'resolve', out
          input.push (err) => res 'reject',  err
          input.push (out) => res 'notify',  out
        else if typeof input == 'object'
          input.done   = (out) => res 'resolve', out
          input.fail   = (err) => res 'reject',  err
          input.update = (out) => res 'notify',  out

          input = [ input ]
        else
          msg = "input to #{proto.constructor.name}.#{method} must be an Array of Object"
          @warn 'input.invalid', msg
          throw new Error msg

        proto._report proto.constructor.name, method, 'invoke', id, input

        input

      _do_wrap: (proto, method) =>
        if method != 'fire' && method != 'warn' && method != 'listen'
          Madul.FIRE "$.#{proto.constructor.name}.#{method}.wrap"

          if typeof proto[method] == 'function'
            proto["_#{method}"] = proto[method]

            proto[method] = =>
              def  = q.defer()
              args = if arguments[0]? then Array.prototype.slice.call arguments else [ ]

              proto["_#{method}"].apply @, proto._prep_invocation proto, method, args, def

              def.promise
          else if typeof proto[method] == 'object'

            if Array.isArray proto[method].validate
              args_format = 'ARRAY'
              decs        = for val in proto[method].validate
                @_parse_handle(val).ref

              proto[method].validate = decs
            else if typeof proto[method].validate == 'object'
              args_format = 'OBJECT'
              decs        = for own key, val of proto[method].validate
                { ref } = @_parse_handle val
                proto[method].validate[key] = ref
                ref
            else if typeof proto[method].validate == 'string'
              args_format = 'ARRAY'
              decs        = [ @_parse_handle(proto[method].validate).ref ]
            else if typeof proto[method].validate != 'undefined'
              @warn 'meta.invalid', validate: 'must be a String, Object, or Array'
              return
            else
              args_format = 'ARRAY'
              decs        = [ ]

            decs = decs.concat(proto[method].before.map (b, i) =>
              { ref } = @_parse_handle b
              proto[method].before[i] = ref
              ref
            ) if proto[method].before?

            decs = decs.concat(proto[method].after.map (a, i) =>
              { ref } = @_parse_handle a
              proto[method].after[i] = ref
              ref
            ) if proto[method].after?

            Madul.FIRE '$.Madul.decorators.hydrate', decs

            @_do_hydrate proto, decs, =>
              proto["_#{method}"] = proto[method]

              proto[method] = =>
                def = q.defer()
                me  = proto["_#{method}"]

                if args_format == 'ARRAY'
                  args = Array.prototype.slice.call arguments

                  if me.validate?
                    validators = for val, i in me.validate
                      { ref } = @_parse_handle val
                      Madul.FIRE '$.Madul.validator.execute', "#{ref}": args[i]
                      proto[ref].EXECUTE args[i]
                else if args_format == 'OBJECT'
                  args = arguments[0]

                  if me.validate?
                    validators = for own key, val of me.validate
                      { ref } = @_parse_handle val
                      Madul.FIRE '$.Madul.validator.execute', "#{ref}": args[key]
                      proto[ref].EXECUTE args[key]
                else
                  @warn 'cannot-continue', 'No arg format specified'

                  return def.reject 'No arg format specified'

                me.before = [ ] unless me.before?
                me.after  = [ ] unless me.after?

                q.all validators
                .then =>
                  q.all me.before.map (b) =>
                    Madul.FIRE '$.Madul.before_filter.execute', "#{b}": args
                    proto[b].before args
                .then =>
                  me.behavior.apply @, @_prep_invocation proto, method, args, def
                .then (result) =>
                  if me.after.length > 0
                    q.all me.after.map (b) =>
                      Madul.FIRE '$.Madul.after_filter.execute', "#{b}": result
                      b.after result
                  else
                    d = q.defer()

                    process.nextTick => d.resolve result

                    d.promise
                .then  (out) => def.resolve out
                .catch (err) => def.reject  err

                def.promise
          else
            @warn 'cannot-wrap', method

          WRAPPED[proto.constructor.name].push method

      _wrap_methods: (proto, callback) =>
        name    = proto.constructor.name
        to_wrap = [ ]

        while proto? && Object.keys(proto).length > 0 && WRAPPED[name]? == false
          to_wrap.push { proto, name, methods: [ ] }

          for own prop, body of proto
            if prop[0]                  != '_'         &&
               typeof proto["_#{prop}"] == 'undefined' &&
               WRAP(name, prop)         == true

              continue if proto.deps? && proto.deps.indexOf(prop.replace(/_/g, '-')) > -1

              if typeof body == 'function' || typeof body?.behavior == 'function'
                to_wrap[to_wrap.length - 1].methods.push prop

          proto = proto.__proto__
          name  = proto.constructor.name

        async.each to_wrap.reverse(), (wrap, completed) =>
          async.each wrap.methods, (method, next) =>
            wrap.proto._do_wrap wrap.proto, method

            INITIALIZERS wrap.name, method if method[0] == '$'

            next()
          , => @_call_initializers_for wrap.proto, wrap.name, completed
        , callback

      _make_available: (name, mod) =>
        Madul.FIRE "$.#{name}.available"

        available[strip name] = mod

      _hydrate_deps: (proto, done) =>
        protos = [ proto ]

        if proto.__proto__?
          while proto.__proto__? && Object.keys(proto.__proto__).length > 0
            protos.push proto = proto.__proto__

        async.each protos.reverse(), (p, next) =>
          name = p.constructor.name

          if p.hasOwnProperty 'deps'
            if HYDRATED[name] == undefined
              HYDRATED[name]            = false
              HYRDATION_LISTENERS[name] = [ next ]

              p._do_hydrate p, p.deps, =>
                HYDRATED[name] = true

                for listener in HYRDATION_LISTENERS[name]
                  listener()
            else if HYDRATED[name] == false
              HYRDATION_LISTENERS[name].push next
            else if HYDRATED[name] == true
              next()
          else
            next()
        , done

      _init_if_madul: (path, callback) =>
        mod      = require path
        proto    = mod
        is_madul = false

        while proto
          is_madul = true if proto.name == 'Madul'
          if is_madul                            == false      &&
             proto.constructor.name              != 'Object'   &&
             typeof proto                        == 'function' &&
             typeof proto.__super__?.constructor == 'function'
            proto = proto.__super__.constructor
          else
            proto = undefined

        if is_madul
          new mod()
            .initialize()
            .then callback
        else
          callback mod

      _load: (me, name, path, loaded) =>
        me._init_if_madul path, (mod) =>
          me._make_available name, mod
          loaded mod

      _check: (me, path, dep, ref, finished) =>
        fs.readdir path, (err, files) =>
          if err?
            me.warn 'file-not-found', err

            done type: 'ERROR', info: err
          else
            async.each files, (f, next) =>
              depth = "#{path}/#{f}"

              fs.stat depth, (e, s) =>
                if s.isDirectory() && f[0] != '.'
                  me._check me, depth, dep, ref, next
                else if s.isFile() && f.substring(0, f.length - 3) == dep
                  me._load me, ref, depth, (mod) => me._do_add me, mod, ref, next
                else
                  next()
            , finished

      _do_add: (me, mod, ref, next) =>
        Madul.FIRE "$.#{me.constructor.name}.dependency.register", ref

        me[underscore ref] = mod

        next()

      _add: (me, ref, path, next) =>
        me._init_if_madul path, (mod) =>
          me._make_available ref, mod
          me._do_add me, mod, ref, next

      _parse_handle: (value) =>
        tokens = value.split '='

        if tokens.length == 2
          initer = tokens[1].trim()
          t      = tokens[0].split '->'

          if t[0].indexOf('#') > -1
            r = t[0].split '#'

            root = SEARCH_ROOTS[r[0].trim()]
            t[0] = r[1]

          if t.length == 2
            name  = t[0].trim()
            alias = t[1].trim()
          else if t.length == 1
            name = alias = t[0].trim()
          else
            return next @warn 'alias.invalid', tokens[1]

          toks = initer.split ':'

          if toks.length == 2
            initer = toks[0].trim()
            pres   = toks[1].split(',').map (p) => p.trim()
          else if toks.length == 1
            initer = toks[0].trim()
          else
            return next @warn 'dependency-initializer.invalid', tokens[1]

        else if tokens.length == 1
          t = tokens[0].split '->'

          if t[0].indexOf('#') > -1
            r = t[0].split '#'

            root = SEARCH_ROOTS[r[0].trim()]
            t[0] = r[1]

          if t.length == 2
            name  = t[0].trim()
            alias = t[1].trim()
          else if t.length == 1
            name = alias = t[0].trim()
          else
            return next @warn 'alias.invalid', tokens[1]

        else
          return next @warn 'dependency.invalid', d

        { ref: alias || name, alias, name, root, initer, pres }

      _do_hydrate: (proto, deps, hydration_complete) =>
        initers = [ ]

        async.each deps, (d, next) =>
          { ref, alias, name, root, initer, pres } = @_parse_handle d

          if pres?
            insert_at = for p in pres
              index_for = (sibling) => sibling.alias == p.alias

              initers.find index_for

            insert_at.sort()

            insert_at = if insert_at.length == 0 then 0 else insert_at[insert_at.length - 1]

            initers.splice insert_at, 0, alias: alias, execute: initer

          if proto[underscore ref]? == false
            if available[strip ref]? == true
              proto._do_add proto, available[strip ref], ref, next
            else
              try
                proto._add proto, ref, name, next
              catch e
                if root?
                  Madul.FIRE '$.Madul.search_root.load', { name, alias, root }

                  proto._check proto, root, name, ref, next
                else
                  cwd = process.cwd()
                  pkg = "#{cwd}/node_modules/#{name}/package.json"

                  fs.stat pkg, (err, stat) =>
                    if stat?.isFile()
                      fs.readFile pkg, 'utf8', (err, data) =>
                        json = JSON.parse data
                        main = json.main || json._main || 'index.js'
                        path = "#{cwd}/node_modules/#{name}/#{main}"

                        proto._add proto, ref, path, next
                    else
                      proto._check proto, "#{cwd}/#{code_root}", name, ref, next
          else
            next()
        , =>
          async.eachSeries initers, (initer, next) =>
            proto[initer.execute].apply(@).then next
          , hydration_complete

      _finish_up: (proto, args) =>
        name = proto.constructor.name

        if listeners[name]?
          async.each listeners[name], (listener, next) =>
            listener @
            next()
          , => @_register_initialized name
        else
          @_register_initialized name

      _register_initialized: (name) =>
        @_make_available name, @

        initialized[name] = true

        Madul.FIRE "$.#{name}.initialized"

      _call_initializers_for: (proto, name, callback) =>
        if _INITIALIZERS[name]?
          async.each _INITIALIZERS[name], (initializer, next) =>
            if initializer.called == false
              proto[initializer.fn].apply @
                .then =>
                  initializer.called = true
                  next()
            else
              next()
          , callback
        else
          callback()

      initialize: =>
        deferred = q.defer()
        proto    = @.__proto__
        name     = proto.constructor.name

        Madul.FIRE "$.#{name}.request_instance"

        if initialized[name] == undefined
          Madul.FIRE "$.#{name}.initialize"

          initialized[name] = false
          listeners[name]   = [ deferred.resolve ]

          @_hydrate_deps proto, => @_wrap_methods proto, => @_finish_up proto
        else if initialized[name] == false
          listeners[name].push deferred.resolve
        else if initialized[name] == true
          process.nextTick => deferred.resolve available[strip name]

        deferred.promise

    module.exports = Madul