/**
* set the context on the statemachine and provide bidirectional
* association.
*
* change the context for a statemachine that already has a context.
* When the context is changed, but it is for the same statemachine (with
* the same transitions), the statemachine can be used directly with the
* new context.
*
* The current state is reset to whatever state the machine should be in
* (either the initial state or the stored state) whenever a context change
* is made.
*
* we can change context to:
* - switch builders/persistence adapters at runtime
* - reuse the statemachine for a different entity so we do not
* have to load the statemachine with the same transition definitions
*
* @param Context $context
* @throws Exception
*/
public function setContext(Context $context)
{
if ($this->getContext()) {
// context already exists.
if ($this->getContext()->getMachine() !== $context->getMachine()) {
throw new Exception(sprintf("Trying to set context for a different machine. currently '%s' and new '%s'", $this->getContext()->getMachine(), $context->getMachine()), Exception::SM_CONTEXT_DIFFERENT_MACHINE);
}
// reset state TODO: move outside if statement
$this->state = null;
}
$context->setStateMachine($this);
$this->context = $context;
}