]> git.mxchange.org Git - core.git/blob - framework/main/classes/resolver/command/class_BaseCommandResolver.php
Continued:
[core.git] / framework / main / classes / resolver / command / class_BaseCommandResolver.php
1 <?php
2 // Own namespace
3 namespace Org\Mxchange\CoreFramework\Resolver\Command;
4
5 // Import framework stuff
6 use Org\Mxchange\CoreFramework\Bootstrap\FrameworkBootstrap;
7 use Org\Mxchange\CoreFramework\Command\Commandable;
8 use Org\Mxchange\CoreFramework\Command\InvalidCommandException;
9 use Org\Mxchange\CoreFramework\Factory\ObjectFactory;
10 use Org\Mxchange\CoreFramework\Request\Requestable;
11 use Org\Mxchange\CoreFramework\Resolver\BaseResolver;
12
13 // Import SPL stuff
14 use \InvalidArgumentException;
15 use \UnexpectedValueException;
16
17 /**
18  * A generic command resolver class
19  *
20  * @author              Roland Haeder <webmaster@shipsimu.org>
21  * @version             0.0.0
22  * @copyright   Copyright (c) 2007, 2008 Roland Haeder, 2009 - 2020 Core Developer Team
23  * @license             GNU GPL 3.0 or any newer version
24  * @link                http://www.shipsimu.org
25  *
26  * This program is free software: you can redistribute it and/or modify
27  * it under the terms of the GNU General Public License as published by
28  * the Free Software Foundation, either version 3 of the License, or
29  * (at your option) any later version.
30  *
31  * This program is distributed in the hope that it will be useful,
32  * but WITHOUT ANY WARRANTY; without even the implied warranty of
33  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
34  * GNU General Public License for more details.
35  *
36  * You should have received a copy of the GNU General Public License
37  * along with this program. If not, see <http://www.gnu.org/licenses/>.
38  */
39 abstract class BaseCommandResolver extends BaseResolver {
40         /**
41          * Command name
42          */
43         private $commandName = '';
44
45         /**
46          * Protected constructor
47          *
48          * @param       $className      Name of the class
49          * @return      void
50          */
51         protected function __construct (string $className) {
52                 // Call parent constructor
53                 parent::__construct($className);
54         }
55
56         /**
57          * Setter for command name
58          *
59          * @param       $commandName    Last validated command name
60          * @return      void
61          */
62         protected final function setCommandName (string $commandName) {
63                 $this->commandName = $commandName;
64         }
65
66         /**
67          * Getter for command name
68          *
69          * @return      $commandName    Last validated command name
70          */
71         protected final function getCommandName () {
72                 return $this->commandName;
73         }
74
75         /**
76          * "Loads" a given command and instances it if not yet cached
77          *
78          * @param       $commandName                            A command name we shall look for
79          * @return      $commandInstance                        A loaded command instance
80          * @throws      InvalidCommandException         Thrown if even the default
81          *                                                                              command class is missing (bad!)
82          */
83         protected function loadCommand ($commandName) {
84                 // Init command instance
85                 $commandInstance = NULL;
86
87                 // Create class name
88                 $className = sprintf(
89                         '%s\%s%sCommand',
90                         $this->getNamespace(),
91                         $this->getCapitalizedClassPrefix(),
92                         self::convertToClassName($commandName)
93                 );
94
95                 // Create command class name
96                 $this->setClassName($className);
97
98                 // Is this class loaded?
99                 if (!class_exists($this->getClassName())) {
100                         // Class not found, so throw an exception
101                         throw new InvalidCommandException(array($this, $commandName), self::EXCEPTION_INVALID_COMMAND);
102                 } // END - if
103
104                 // Initiate the command
105                 $commandInstance = ObjectFactory::createObjectByName($this->getClassName(), array($this));
106
107                 // Return the result
108                 return $commandInstance;
109         }
110
111         /**
112          * Returns an command instance for a given request class or null if
113          * it was not found
114          *
115          * @param       $requestInstance        An instance of a Requestable class
116          * @return      $commandInstance        An instance of the resolved command
117          * @throws      InvalidCommandException         Thrown if $commandName is invalid
118          * @throws      UnexpectedValueException        Thrown if $commandInstance is an invalid instance
119          */
120         public function resolveCommandByRequest (Requestable $requestInstance) {
121                 // Init variables
122                 $commandName = '';
123                 $commandInstance = NULL;
124
125                 // This goes fine so let's resolve the command
126                 $commandName = $requestInstance->getRequestElement('command');
127
128                 // Is the command empty? Then fall back to default command
129                 if (empty($commandName)) {
130                         $commandName = FrameworkBootstrap::getConfigurationInstance()->getConfigEntry('default_' . FrameworkBootstrap::getRequestTypeFromSystem() . '_command');
131                 } // END - if
132
133                 // Check if command is valid
134                 if ($this->isCommandValid($this->getNamespace(), $commandName) === false) {
135                         // This command is invalid!
136                         throw new InvalidCommandException(array($this, $commandName), self::EXCEPTION_INVALID_COMMAND);
137                 } // END - if
138
139                 // Get the command
140                 $commandInstance = $this->loadCommand($commandName);
141
142                 // And validate it
143                 if ((!is_object($commandInstance)) || (!$commandInstance instanceof Commandable)) {
144                         // This command has an invalid instance!
145                         throw new UnexpectedValueException(sprintf('commandInstance for commandName=%s is not object (%s) or does not implement Commandable.', $commandName, gettype($commandInstance)), self::EXCEPTION_INVALID_COMMAND);
146                 } // END - if
147
148                 // Set last command
149                 $this->setResolvedInstance($commandInstance);
150
151                 // Return the resolved command instance
152                 return $commandInstance;
153         }
154
155         /**
156          * Resolves the command by its direct name and returns an instance of its class
157          *
158          * @param       $namespace                      Namespace to look in
159          * @param       $commandName            The direct command name we shall resolve
160          * @return      $commandInstance        An instance of the command class
161          * @throws      InvalidCommandException         Thrown if $commandName is invalid
162          */
163         public function resolveCommand ($namespace, $commandName) {
164                 // Is a action set?
165                 if (empty($namespace)) {
166                         // Then thrown an exception here
167                         throw new InvalidArgumentException('Parameter "namespace" is empty');
168                 } elseif (empty($commandName)) {
169                         // Then thrown an exception here
170                         throw new InvalidArgumentException('Parameter "commandName" is empty');
171                 }
172
173                 // Initiate the instance variable
174                 $commandInstance = NULL;
175
176                 // Is the command empty? Then fall back to default command
177                 if (empty($commandName)) {
178                         // Init default command
179                         $commandName = FrameworkBootstrap::getConfigurationInstance()->getConfigEntry('default_' . FrameworkBootstrap::getRequestTypeFromSystem() . '_command');
180                 } // END - if
181
182                 // Check if command is valid
183                 if ($this->isCommandValid($namespace, $commandName) === false) {
184                         // This command is invalid!
185                         throw new InvalidCommandException(array($this, $commandName), self::EXCEPTION_INVALID_COMMAND);
186                 } // END - if
187
188                 // Get the command
189                 $commandInstance = $this->loadCommand($commandName);
190
191                 // Return the instance
192                 return $commandInstance;
193         }
194
195         /**
196          * Checks whether the given command is valid
197          *
198          * @param       $namespace              Namespace to look in
199          * @param       $commandName    The default command we shall execute
200          * @return      $isValid                Whether the given command is valid
201          * @throws      InvalidArgumentException        Thrown if given command is not set
202          */
203         protected function isCommandValid ($namespace, $commandName) {
204                 // Is namespace and command name set?
205                 if (empty($namespace)) {
206                         // Then thrown an exception here
207                         throw new InvalidArgumentException('Parameter "namespace" is empty');
208                 } elseif (empty($commandName)) {
209                         // Then thrown an exception here
210                         throw new InvalidArgumentException('Parameter "commandName" is empty');
211                 }
212
213                 // By default nothing shall be valid
214                 $isValid = false;
215
216                 // Create the full class name
217                 $className = sprintf(
218                         '%s\%s%sCommand',
219                         $namespace,
220                         $this->getCapitalizedClassPrefix(),
221                         self::convertToClassName($commandName)
222                 );
223
224                 // Now, let us create the full name of the command class
225                 $this->setClassName($className);
226
227                 // Is this class already loaded?
228                 if (class_exists($this->getClassName())) {
229                         // This class does exist. :-)
230                         $isValid = true;
231                 } // END - if
232
233                 // Set command name
234                 $this->setCommandName($commandName);
235
236                 // Return the result
237                 return $isValid;
238         }
239
240 }