Give snapshots states of their own, and update the noderole state machine to reflect that. [1/2]

This pull request gives snapshots their own states.

Previously, the state of a snapshot was derived exclusively from the
noderoles that they wrapped.  However, that failed to help control how
to manage the noderoles in a deployment when we had more than one
snapshot.  The most straightforward way to handle this was to give
snapshots their own states, and to use that to control when a noderole
was editable and to manage what the annealer would care about and try
to traverse.

Snapshots now have 3 primary states:
* PROPOSED:  All snapshots on non-system deployments start in the
  PROPOSED state.  When in this state, the annealer will ignore any
  noderoles in the snapshot, no hooks will be called for any state
  transitions, and user data for the node roles can be edited.
* COMMITTED:  When a snapshot is in committed, userdata in node roles
  cannot be edited, the annealer will transition any nodes in TODO,
  and hooks will be called for any state transitions.
* ARCHIVED:  Snapshots in archived state will be ignored by the
  annealer and by just about everything.  Eventually you will be able
  to look through them to satisfy your curiosity about the past states
  of the cluster. 

There are two other states that are substates of the COMMITTED state
that are primarily for consumption by the UI:
* ACTIVE, which is when all of the noderoles in a COMMITTED snapshot
are in the ACTIVE state, and
* ERROR, when any noderole in a COMMITTED snapshot is in the ERROR
state.

State transitions for snapshots:

* (previous snapshot) -> PROPOSED:  The previous snapshot is set to
  ARCHIVED. The new snapshot gets a copy of all the noderoles in the
  previous snapshot, which will have the same data and the same states
  as the old ones.  
* PROPOSED -> COMMITTED:  All PROPOSED noderoles in the snapshot are
  transitioned to TODO or BLOCKED, depending on whether or not they
  have any non-active parents.  The only way to go from proposed to
  committed is via the commit method for the snapshot.
* COMMITTED -> PROPOSED: The only way to go from COMMITTED to PROPOSED
is via the snapshot recall method.
* (COMMITTED || PROPOSED) -> ARCHIVED:  A snapshot gets transitioned
  to ARCHIVED when it is superceded by a new snapshot.  Archived
  snapshots are ignored.


The system deployment is super-special in that its snapshots can not
be transitioned to PROPOSED.


 .../app/controllers/node_roles_controller.rb       |   18 +--
 .../app/controllers/nodes_controller.rb            |    4 +-
 crowbar_framework/app/models/node_role.rb          |   96 +++++++-------
 crowbar_framework/app/models/snapshot.rb           |  133 ++++++++++++--------
 .../app/views/deployments/_buttons.html.haml       |   14 +--
 .../app/views/deployments/index.html.haml          |    2 +-
 .../app/views/deployments/show.html.haml           |    4 +-
 .../app/views/snapshots/_index.html.haml           |    4 +-
 .../app/views/snapshots/show.html.haml             |    6 +-
 .../config/initializers/crowbar_deployment.rb      |    1 +
 crowbar_framework/config/locales/crowbar/en.yml    |    2 +
 .../db/migrate/20120731225476_create_snapshots.rb  |    4 +-
 crowbar_framework/spec/models/node_spec.rb         |    1 +
 .../shared_contexts/base_deployement_nodes.rb      |   15 ++-
 .../shared_contexts/test_bc_with_2_nodes.rb        |    2 +-
 15 files changed, 173 insertions(+), 133 deletions(-)

Crowbar-Pull-ID: 9fc9a35a19bcde0e9191c1b957eded3f6024f5b9

Crowbar-Release: development