Skip to content

Commit 146db30

Browse files
committed
Refactor module
1 parent 0a7068a commit 146db30

File tree

2 files changed

+77
-48
lines changed

2 files changed

+77
-48
lines changed

sources/Module/MarkupValidator.php

Lines changed: 59 additions & 45 deletions
Original file line numberDiff line numberDiff line change
@@ -3,8 +3,10 @@
33
namespace Kolyunya\Codeception\Module;
44

55
use Exception;
6+
use ReflectionClass;
67
use Codeception\Lib\ModuleContainer;
78
use Codeception\Module;
9+
use Kolyunya\Codeception\Lib\Base\ComponentInterface;
810
use Kolyunya\Codeception\Lib\MarkupValidator\MarkupProviderInterface;
911
use Kolyunya\Codeception\Lib\MarkupValidator\MarkupReporterInterface;
1012
use Kolyunya\Codeception\Lib\MarkupValidator\MarkupValidatorInterface;
@@ -14,15 +16,22 @@
1416
*/
1517
class MarkupValidator extends Module
1618
{
19+
20+
const COMPONENT_CLASS_CONFIG_KEY = 'class';
21+
22+
const COMPONENT_CONFIG_CONFIG_KEY = 'config';
23+
24+
const PROVIDER_INTERFACE = 'Kolyunya\Codeception\Lib\MarkupValidator\MarkupProviderInterface';
1725
const PROVIDER_CONFIG_KEY = 'provider';
1826

27+
const VALIDATOR_INTERFACE = 'Kolyunya\Codeception\Lib\MarkupValidator\MarkupValidatorInterface';
1928
const VALIDATOR_CONFIG_KEY = 'validator';
2029

30+
const REPORTER_INTERFACE = 'Kolyunya\Codeception\Lib\MarkupValidator\MarkupReporterInterface';
2131
const REPORTER_CONFIG_KEY = 'reporter';
2232

23-
const COMPONENT_CLASS_CONFIG_KEY = 'class';
24-
25-
const COMPONENT_CONFIG_CONFIG_KEY = 'config';
33+
const PRINTER_INTERFACE = 'Kolyunya\Codeception\Lib\MarkupValidator\MessagePrinterInterface';
34+
const PRINTER_CONFIG_KEY = 'printer';
2635

2736
/**
2837
* {@inheritDoc}
@@ -95,38 +104,64 @@ public function validateMarkup(array $reporterConfiguration = array())
95104
*/
96105
private function initializeProvider()
97106
{
98-
$providerName = self::PROVIDER_CONFIG_KEY;
99-
$providerClass = $this->getComponentClass($providerName);
100-
$providerConfig = $this->getComponentConfig($providerName);
101-
$this->provider = new $providerClass($this->moduleContainer, $providerConfig);
102-
$providerInterface = 'Kolyunya\Codeception\Lib\MarkupValidator\MarkupProviderInterface';
103-
$this->validateComponentInstance($this->provider, $providerInterface, $providerName);
107+
$this->provider = $this->instantiateComponent(
108+
self::PROVIDER_CONFIG_KEY,
109+
self::PROVIDER_INTERFACE,
110+
array(
111+
$this->moduleContainer,
112+
)
113+
);
104114
}
105115

106116
/**
107117
* Initializes markup validator.
108118
*/
109119
private function initializeValidator()
110120
{
111-
$validatorName = self::VALIDATOR_CONFIG_KEY;
112-
$validatorClass = $this->getComponentClass($validatorName);
113-
$validatorConfig = $this->getComponentConfig($validatorName);
114-
$this->validator = new $validatorClass($validatorConfig);
115-
$validatorInterface = 'Kolyunya\Codeception\Lib\MarkupValidator\MarkupValidatorInterface';
116-
$this->validateComponentInstance($this->validator, $validatorInterface, $validatorName);
121+
$this->validator = $this->instantiateComponent(
122+
self::VALIDATOR_CONFIG_KEY,
123+
self::VALIDATOR_INTERFACE
124+
);
117125
}
118126

119127
/**
120-
* Initializes markup validator.
128+
* Initializes markup reporter.
121129
*/
122130
private function initializeReporter()
123131
{
124-
$reporterName = self::REPORTER_CONFIG_KEY;
125-
$reporterClass = $this->getComponentClass($reporterName);
126-
$reporterConfig = $this->getComponentConfig($reporterName);
127-
$this->reporter = new $reporterClass($reporterConfig);
128-
$reporterInterface = 'Kolyunya\Codeception\Lib\MarkupValidator\MarkupReporterInterface';
129-
$this->validateComponentInstance($this->reporter, $reporterInterface, $reporterName);
132+
$this->reporter = $this->instantiateComponent(
133+
self::REPORTER_CONFIG_KEY,
134+
self::REPORTER_INTERFACE
135+
);
136+
}
137+
138+
/**
139+
* Instantiates and returns a module component.
140+
*
141+
* @param string $componentName Component name.
142+
* @param string $interface An interface component must implement.
143+
* @param array $arguments Component's constructor arguments.
144+
*
145+
* @throws Exception When component does not implement expected interface.
146+
*
147+
* @return object Instance of a module component.
148+
*/
149+
private function instantiateComponent($componentName, $interface, array $arguments = array())
150+
{
151+
$componentClass = $this->getComponentClass($componentName);
152+
$componentReflectionClass = new ReflectionClass($componentClass);
153+
if ($componentReflectionClass->implementsInterface($interface) === false) {
154+
$errorMessageTemplate = 'Invalid class «%s» provided for component «%s». It must implement «%s».';
155+
$errorMessage = sprintf($errorMessageTemplate, $componentClass, $componentName, $interface);
156+
throw new Exception($errorMessage);
157+
}
158+
159+
/* @var $component ComponentInterface */
160+
$component = $componentReflectionClass->newInstanceArgs($arguments);
161+
$componentConfiguration = $this->getComponentConfiguration($componentName);
162+
$component->setConfiguration($componentConfiguration);
163+
164+
return $component;
130165
}
131166

132167
/**
@@ -156,9 +191,9 @@ private function getComponentClass($componentName)
156191
*
157192
* @param string $componentName Component name.
158193
*
159-
* @return string Component configuration parameters.
194+
* @return array Component configuration parameters.
160195
*/
161-
private function getComponentConfig($componentName)
196+
private function getComponentConfiguration($componentName)
162197
{
163198
$componentConfig = array();
164199

@@ -174,25 +209,4 @@ private function getComponentConfig($componentName)
174209

175210
return $componentConfig;
176211
}
177-
178-
/**
179-
* Ensures that a component is an instance of a specifi interface.
180-
*
181-
* @param object $component Component instance to validate.
182-
* @param string $interface Interface to validate component instance against.
183-
* @param string $componentName Component name. User for error logging.
184-
*
185-
* @throws Exception When `component` is not an instance of the `interface`.
186-
*/
187-
private function validateComponentInstance($component, $interface, $componentName)
188-
{
189-
if (($component instanceof $interface) === false) {
190-
$componentClass = get_class($component);
191-
$errorMessage = vsprintf('Invalid class «%s» provided for component «%s».', array(
192-
$componentClass,
193-
$componentName,
194-
));
195-
throw new Exception($errorMessage);
196-
}
197-
}
198212
}

tests/Module/MarkupValidatorTest.php

Lines changed: 18 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -57,7 +57,12 @@ public function tearDown()
5757

5858
public function testInvalidProvider()
5959
{
60-
$this->setExpectedException('Exception', 'Invalid class «stdClass» provided for component «provider».');
60+
$exceptionTemplate = 'Invalid class «%s» provided for component «%s». It must implement «%s».';
61+
$this->setExpectedException('Exception', vsprintf($exceptionTemplate, array(
62+
'stdClass',
63+
'provider',
64+
'Kolyunya\Codeception\Lib\MarkupValidator\MarkupProviderInterface',
65+
)));
6166

6267
$this->module = new MarkupValidator($this->moduleContainer, array(
6368
'provider' => array(
@@ -68,7 +73,12 @@ public function testInvalidProvider()
6873

6974
public function testInvalidValidator()
7075
{
71-
$this->setExpectedException('Exception', 'Invalid class «stdClass» provided for component «validator».');
76+
$exceptionTemplate = 'Invalid class «%s» provided for component «%s». It must implement «%s».';
77+
$this->setExpectedException('Exception', vsprintf($exceptionTemplate, array(
78+
'stdClass',
79+
'validator',
80+
'Kolyunya\Codeception\Lib\MarkupValidator\MarkupValidatorInterface',
81+
)));
7282

7383
$this->module = new MarkupValidator($this->moduleContainer, array(
7484
'validator' => array(
@@ -79,7 +89,12 @@ public function testInvalidValidator()
7989

8090
public function testInvalidReporter()
8191
{
82-
$this->setExpectedException('Exception', 'Invalid class «stdClass» provided for component «reporter».');
92+
$exceptionTemplate = 'Invalid class «%s» provided for component «%s». It must implement «%s».';
93+
$this->setExpectedException('Exception', vsprintf($exceptionTemplate, array(
94+
'stdClass',
95+
'reporter',
96+
'Kolyunya\Codeception\Lib\MarkupValidator\MarkupReporterInterface',
97+
)));
8398

8499
$this->module = new MarkupValidator($this->moduleContainer, array(
85100
'reporter' => array(

0 commit comments

Comments
 (0)