/** * returns the associated Command for the entry/exit/transition action on a * State or a Transition. * the Command will be configured with the 'reference' of the stateful * object * * @param string $command_name * entry~,exit~ or transition command name. * multiple commands can be split by a ',' in which case a * composite command will be returned. * @param Context $context * to be able to get the entity * @return ICommand * @throws Exception */ public static function getCommand($command_name, Context $context) { // it's oke to have no command, as there might be 'marker' states, where // we just need to transition something to a next state (according to a // rule) // where useful work can be done (eg: from the 'initial' type state to // a 'shortcut' state for special cases. if ($command_name === '' || $command_name === null) { // return a command without side effects return new Null(); } $output = new Composite(); // a command string can be made up of multiple commands seperated by a // comma $all_commands = explode(',', $command_name); // get the correct object to inject in the command(s) $entity = $context->getEntity(); foreach ($all_commands as $single_command) { if (!class_exists($single_command)) { $e = new Exception(sprintf("failed command creation, class does not exist: (%s) for Context (%s)", $single_command, $context->toString()), Exception::COMMAND_CREATION_FAILURE); throw $e; } try { $command = new $single_command($entity); $output->add($command); } catch (\Exception $e) { $e = new Exception(sprintf("command (%s) objects to construction for Context (%s). message: '%s'", $single_command, $context->toString(), $e->getMessage()), Exception::COMMAND_CREATION_FAILURE); throw $e; } } return $output; }
public function testCompositeCommand() { $composite = new Composite(); //test basics of this command $this->assertTrue(is_subclass_of($composite, 'izzum\\command\\Command')); $this->assertTrue(in_array('izzum\\command\\IComposite', class_implements($composite))); $this->assertTrue(in_array('izzum\\command\\ICommand', class_implements($composite))); $list = array(); //create 3 commands with a reference to the same list $command1 = new AddToListCommand($list); $command2 = new AddToListCommand($list); $command3 = new AddToListCommand($list); //executing the composite does not affect list $composite->execute(); $this->assertEquals(0, count($list)); //add commands to composite 'in order' $composite->add($command1); $composite->add($command2); $composite->add($command3); //execute the composite, we expect to have an array with incrementing numbers, //proving the composite executes 'in order' $composite->execute(); $this->assertEquals(3, count($list)); $this->assertTrue($list[1] == $list[0] + 1); $this->assertTrue($list[2] == $list[1] + 1); $list = array(); $command1 = new AddToListCommand($list); $command2 = new AddToListCommand($list); $command3 = new AddToListCommand($list); $composite = new Composite(); //add the commands one by one and check everything works out //check add() and contains() $composite->add($command1); $this->assertTrue($composite->contains($command1)); $this->assertFalse($composite->contains($command2)); $this->assertFalse($composite->contains($command3)); $composite->add($command2); $this->assertTrue($composite->contains($command1)); $this->assertTrue($composite->contains($command2)); $this->assertFalse($composite->contains($command3)); $composite->add($command3); $this->assertTrue($composite->contains($command1)); $this->assertTrue($composite->contains($command2)); $this->assertTrue($composite->contains($command3)); //remove one by one //check remove() and contains() $this->assertEquals(3, $composite->count()); $composite->remove($command1); $this->assertFalse($composite->contains($command1)); $this->assertTrue($composite->contains($command2)); $this->assertTrue($composite->contains($command3)); $composite->remove($command2); $this->assertFalse($composite->contains($command1)); $this->assertFalse($composite->contains($command2)); $this->assertTrue($composite->contains($command3)); $composite->remove($command3); $this->assertFalse($composite->contains($command1)); $this->assertFalse($composite->contains($command2)); $this->assertFalse($composite->contains($command3)); $this->assertNotNull($composite->toString()); //nested composite $composite = new Composite(); $nested = new Composite(); $composite->add($nested); $this->assertNotNull($composite->toString()); }