5
									
								
								vendor/phpspec/prophecy/.gitignore
									
									
									
									
										vendored
									
									
								
							
							
						
						
									
										5
									
								
								vendor/phpspec/prophecy/.gitignore
									
									
									
									
										vendored
									
									
								
							| @@ -1,5 +0,0 @@ | ||||
| *.tgz | ||||
| *.phar | ||||
| bin | ||||
| vendor | ||||
| composer.lock | ||||
							
								
								
									
										15
									
								
								vendor/phpspec/prophecy/.travis.yml
									
									
									
									
										vendored
									
									
								
							
							
						
						
									
										15
									
								
								vendor/phpspec/prophecy/.travis.yml
									
									
									
									
										vendored
									
									
								
							| @@ -1,15 +0,0 @@ | ||||
| language: php | ||||
|  | ||||
| php: [5.3, 5.4, 5.5, hhvm, hhvm-nightly] | ||||
|  | ||||
| sudo: false | ||||
|  | ||||
| branches: | ||||
|   except: | ||||
|     - /^bugfix\/.*$/ | ||||
|     - /^feature\/.*$/ | ||||
|     - /^optimization\/.*$/ | ||||
|  | ||||
| before_script: travis_retry composer install --no-interaction --prefer-source | ||||
|  | ||||
| script: vendor/bin/phpspec run -fpretty -v | ||||
							
								
								
									
										115
									
								
								vendor/phpspec/prophecy/CHANGES.md
									
									
									
									
										vendored
									
									
								
							
							
						
						
									
										115
									
								
								vendor/phpspec/prophecy/CHANGES.md
									
									
									
									
										vendored
									
									
								
							| @@ -1,115 +0,0 @@ | ||||
| 1.4.1 / 2015-04-27 | ||||
| ================== | ||||
|  | ||||
|   * Fixed bug in closure-based argument tokens (#181) | ||||
|  | ||||
| 1.4.0 / 2015-03-27 | ||||
| ================== | ||||
|  | ||||
|   * Fixed errors in return type phpdocs (thanks @sobit) | ||||
|   * Fixed stringifying of hash containing one value (thanks @avant1) | ||||
|   * Improved clarity of method call expectation exception (thanks @dantleech) | ||||
|   * Add ability to specify which argument is returned in willReturnArgument (thanks @coderbyheart) | ||||
|   * Add more information to MethodNotFound exceptions (thanks @ciaranmcnulty) | ||||
|   * Support for mocking classes with methods that return references (thanks @edsonmedina) | ||||
|   * Improved object comparison (thanks @whatthejeff) | ||||
|   * Adopted '^' in composer dependencies (thanks @GrahamCampbell) | ||||
|   * Fixed non-typehinted arguments being treated as optional (thanks @whatthejeff) | ||||
|   * Magic methods are now filtered for keywords (thanks @seagoj) | ||||
|   * More readable errors for failure when expecting single calls (thanks @dantleech) | ||||
|  | ||||
| 1.3.1 / 2014-11-17 | ||||
| ================== | ||||
|  | ||||
|   * Fix the edge case when failed predictions weren't recorded for `getCheckedPredictions()` | ||||
|  | ||||
| 1.3.0 / 2014-11-14 | ||||
| ================== | ||||
|  | ||||
|   * Add a way to get checked predictions with `MethodProphecy::getCheckedPredictions()` | ||||
|   * Fix HHVM compatibility | ||||
|   * Remove dead code (thanks @stof) | ||||
|   * Add support for DirectoryIterators (thanks @shanethehat) | ||||
|  | ||||
| 1.2.0 / 2014-07-18 | ||||
| ================== | ||||
|  | ||||
|   * Added support for doubling magic methods documented in the class phpdoc (thanks @armetiz) | ||||
|   * Fixed a segfault appearing in some cases (thanks @dmoreaulf) | ||||
|   * Fixed the doubling of methods with typehints on non-existent classes (thanks @gquemener) | ||||
|   * Added support for internal classes using keywords as method names (thanks @milan) | ||||
|   * Added IdenticalValueToken and Argument::is (thanks @florianv) | ||||
|   * Removed the usage of scalar typehints in HHVM as HHVM 3 does not support them anymore in PHP code (thanks @whatthejeff) | ||||
|  | ||||
| 1.1.2 / 2014-01-24 | ||||
| ================== | ||||
|  | ||||
|   * Spy automatically promotes spied method call to an expected one | ||||
|  | ||||
| 1.1.1 / 2014-01-15 | ||||
| ================== | ||||
|  | ||||
|   * Added support for HHVM | ||||
|  | ||||
| 1.1.0 / 2014-01-01 | ||||
| ================== | ||||
|  | ||||
|   * Changed the generated class names to use a static counter instead of a random number | ||||
|   * Added a clss patch for ReflectionClass::newInstance to make its argument optional consistently (thanks @docteurklein) | ||||
|   * Fixed mirroring of classes with typehints on non-existent classes (thanks @docteurklein) | ||||
|   * Fixed the support of array callables in CallbackPromise and CallbackPrediction (thanks @ciaranmcnulty) | ||||
|   * Added support for properties in ObjectStateToken (thanks @adrienbrault) | ||||
|   * Added support for mocking classes with a final constructor (thanks @ciaranmcnulty) | ||||
|   * Added ArrayEveryEntryToken and Argument::withEveryEntry() (thanks @adrienbrault) | ||||
|   * Added an exception when trying to prophesize on a final method instead of ignoring silently (thanks @docteurklein) | ||||
|   * Added StringContainToken and Argument::containingString() (thanks @peterjmit) | ||||
|   * Added ``shouldNotHaveBeenCalled`` on the MethodProphecy (thanks @ciaranmcnulty) | ||||
|   * Fixed the comparison of objects in ExactValuetoken (thanks @sstok) | ||||
|   * Deprecated ``shouldNotBeenCalled`` in favor of ``shouldNotHaveBeenCalled`` | ||||
|  | ||||
| 1.0.4 / 2013-08-10 | ||||
| ================== | ||||
|  | ||||
|   * Better randomness for generated class names (thanks @sstok) | ||||
|   * Add support for interfaces into TypeToken and Argument::type() (thanks @sstok) | ||||
|   * Add support for old-style (method name === class name) constructors (thanks @l310 for report) | ||||
|  | ||||
| 1.0.3 / 2013-07-04 | ||||
| ================== | ||||
|  | ||||
|   * Support callable typehints (thanks @stof) | ||||
|   * Do not attempt to autoload arrays when generating code (thanks @MarcoDeBortoli) | ||||
|   * New ArrayEntryToken (thanks @kagux) | ||||
|  | ||||
| 1.0.2 / 2013-05-19 | ||||
| ================== | ||||
|  | ||||
|   * Logical `AND` token added (thanks @kagux) | ||||
|   * Logical `NOT` token added (thanks @kagux) | ||||
|   * Add support for setting custom constructor arguments | ||||
|   * Properly stringify hashes | ||||
|   * Record calls that throw exceptions | ||||
|   * Migrate spec suite to PhpSpec 2.0 | ||||
|  | ||||
| 1.0.1 / 2013-04-30 | ||||
| ================== | ||||
|  | ||||
|   * Fix broken UnexpectedCallException message | ||||
|   * Trim AggregateException message | ||||
|  | ||||
| 1.0.0 / 2013-04-29 | ||||
| ================== | ||||
|  | ||||
|   * Improve exception messages | ||||
|  | ||||
| 1.0.0-BETA2 / 2013-04-03 | ||||
| ======================== | ||||
|  | ||||
|   * Add more debug information to CallTimes and Call prediction exception messages | ||||
|   * Fix MethodNotFoundException wrong namespace (thanks @gunnarlium) | ||||
|   * Fix some typos in the exception messages (thanks @pborreli) | ||||
|  | ||||
| 1.0.0-BETA1 / 2013-03-25 | ||||
| ======================== | ||||
|  | ||||
|   * Initial release | ||||
							
								
								
									
										21
									
								
								vendor/phpspec/prophecy/CONTRIBUTING.md
									
									
									
									
										vendored
									
									
								
							
							
						
						
									
										21
									
								
								vendor/phpspec/prophecy/CONTRIBUTING.md
									
									
									
									
										vendored
									
									
								
							| @@ -1,21 +0,0 @@ | ||||
| Contributing | ||||
| ------------ | ||||
|  | ||||
| Prophecy is an open source, community-driven project. If you'd like to contribute, | ||||
| feel free to do this, but remember to follow this few simple rules: | ||||
|  | ||||
| - Make your feature addition or bug fix, | ||||
| - Add either specs or examples for any changes you're making (bugfixes or additions) | ||||
|   (please look into `spec/` folder for some examples). This is important so we don't break | ||||
|   it in a future version unintentionally, | ||||
| - Commit your code, but do not mess with `CHANGES.md`, | ||||
|  | ||||
| Running tests | ||||
| ------------- | ||||
|  | ||||
| Make sure that you don't break anything with your changes by running: | ||||
|  | ||||
| ```bash | ||||
| $> composer install --dev --prefer-dist | ||||
| $> vendor/bin/phpspec | ||||
| ``` | ||||
							
								
								
									
										23
									
								
								vendor/phpspec/prophecy/LICENSE
									
									
									
									
										vendored
									
									
								
							
							
						
						
									
										23
									
								
								vendor/phpspec/prophecy/LICENSE
									
									
									
									
										vendored
									
									
								
							| @@ -1,23 +0,0 @@ | ||||
| Copyright (c) 2013 Konstantin Kudryashov <ever.zet@gmail.com> | ||||
|                    Marcello Duarte <marcello.duarte@gmail.com> | ||||
|  | ||||
| Permission is hereby granted, free of charge, to any person | ||||
| obtaining a copy of this software and associated documentation | ||||
| files (the "Software"), to deal in the Software without | ||||
| restriction, including without limitation the rights to use, | ||||
| copy, modify, merge, publish, distribute, sublicense, and/or sell | ||||
| copies of the Software, and to permit persons to whom the | ||||
| Software is furnished to do so, subject to the following | ||||
| conditions: | ||||
|  | ||||
| The above copyright notice and this permission notice shall be | ||||
| included in all copies or substantial portions of the Software. | ||||
|  | ||||
| THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, | ||||
| EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES | ||||
| OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND | ||||
| NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT | ||||
| HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, | ||||
| WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING | ||||
| FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR | ||||
| OTHER DEALINGS IN THE SOFTWARE. | ||||
							
								
								
									
										389
									
								
								vendor/phpspec/prophecy/README.md
									
									
									
									
										vendored
									
									
								
							
							
						
						
									
										389
									
								
								vendor/phpspec/prophecy/README.md
									
									
									
									
										vendored
									
									
								
							| @@ -1,389 +0,0 @@ | ||||
| # Prophecy | ||||
|  | ||||
| [](https://travis-ci.org/phpspec/prophecy) | ||||
|  | ||||
| Prophecy is a highly opinionated yet very powerful and flexible PHP object mocking | ||||
| framework. Though initially it was created to fulfil phpspec2 needs, it is flexible | ||||
| enough to be used inside any testing framework out there with minimal effort. | ||||
|  | ||||
| ## A simple example | ||||
|  | ||||
| ```php | ||||
| <?php | ||||
|  | ||||
| class UserTest extends PHPUnit_Framework_TestCase | ||||
| { | ||||
|     private $prophet; | ||||
|  | ||||
|     public function testPasswordHashing() | ||||
|     { | ||||
|         $hasher = $this->prophet->prophesize('App\Security\Hasher'); | ||||
|         $user   = new App\Entity\User($hasher->reveal()); | ||||
|  | ||||
|         $hasher->generateHash($user, 'qwerty')->willReturn('hashed_pass'); | ||||
|  | ||||
|         $user->setPassword('qwerty'); | ||||
|  | ||||
|         $this->assertEquals('hashed_pass', $user->getPassword()); | ||||
|     } | ||||
|  | ||||
|     protected function setup() | ||||
|     { | ||||
|         $this->prophet = new \Prophecy\Prophet; | ||||
|     } | ||||
|  | ||||
|     protected function tearDown() | ||||
|     { | ||||
|         $this->prophet->checkPredictions(); | ||||
|     } | ||||
| } | ||||
| ``` | ||||
|  | ||||
| ## Installation | ||||
|  | ||||
| ### Prerequisites | ||||
|  | ||||
| Prophecy requires PHP 5.3.3 or greater. | ||||
|  | ||||
| ### Setup through composer | ||||
|  | ||||
| First, add Prophecy to the list of dependencies inside your `composer.json`: | ||||
|  | ||||
| ```json | ||||
| { | ||||
|     "require-dev": { | ||||
|         "phpspec/prophecy": "~1.0" | ||||
|     } | ||||
| } | ||||
| ``` | ||||
|  | ||||
| Then simply install it with composer: | ||||
|  | ||||
| ```bash | ||||
| $> composer install --prefer-dist | ||||
| ``` | ||||
|  | ||||
| You can read more about Composer on its [official webpage](http://getcomposer.org). | ||||
|  | ||||
| ## How to use it | ||||
|  | ||||
| First of all, in Prophecy every word has a logical meaning, even the name of the library | ||||
| itself (Prophecy). When you start feeling that, you'll become very fluid with this | ||||
| tool. | ||||
|  | ||||
| For example, Prophecy has been named that way because it concentrates on describing the future | ||||
| behavior of objects with very limited knowledge about them. But as with any other prophecy, | ||||
| those object prophecies can't create themselves - there should be a Prophet: | ||||
|  | ||||
| ```php | ||||
| $prophet = new Prophecy\Prophet; | ||||
| ``` | ||||
|  | ||||
| The Prophet creates prophecies by *prophesizing* them: | ||||
|  | ||||
| ```php | ||||
| $prophecy = $prophet->prophesize(); | ||||
| ``` | ||||
|  | ||||
| The result of the `prophesize()` method call is a new object of class `ObjectProphecy`. Yes, | ||||
| that's your specific object prophecy, which describes how your object would behave | ||||
| in the near future. But first, you need to specify which object you're talking about, | ||||
| right? | ||||
|  | ||||
| ```php | ||||
| $prophecy->willExtend('stdClass'); | ||||
| $prophecy->willImplement('SessionHandlerInterface'); | ||||
| ``` | ||||
|  | ||||
| There are 2 interesting calls - `willExtend` and `willImplement`. The first one tells | ||||
| object prophecy that our object should extend specific class, the second one says that | ||||
| it should implement some interface. Obviously, objects in PHP can implement multiple | ||||
| interfaces, but extend only one parent class. | ||||
|  | ||||
| ### Dummies | ||||
|  | ||||
| Ok, now we have our object prophecy. What can we do with it? First of all, we can get | ||||
| our object *dummy* by revealing its prophecy: | ||||
|  | ||||
| ```php | ||||
| $dummy = $prophecy->reveal(); | ||||
| ``` | ||||
|  | ||||
| The `$dummy` variable now holds a special dummy object. Dummy objects are objects that extend | ||||
| and/or implement preset classes/interfaces by overriding all their public methods. The key | ||||
| point about dummies is that they do not hold any logic - they just do nothing. Any method | ||||
| of the dummy will always return `null` and the dummy will never throw any exceptions. | ||||
| Dummy is your friend if you don't care about the actual behavior of this double and just need | ||||
| a token object to satisfy a method typehint. | ||||
|  | ||||
| You need to understand one thing - a dummy is not a prophecy. Your object prophecy is still | ||||
| assigned to `$prophecy` variable and in order to manipulate with your expectations, you | ||||
| should work with it. `$dummy` is a dummy - a simple php object that tries to fulfil your | ||||
| prophecy. | ||||
|  | ||||
| ### Stubs | ||||
|  | ||||
| Ok, now we know how to create basic prophecies and reveal dummies from them. That's | ||||
| awesome if we don't care about our _doubles_ (objects that reflect originals) | ||||
| interactions. If we do, we need to use *stubs* or *mocks*. | ||||
|  | ||||
| A stub is an object double, which doesn't have any expectations about the object behavior, | ||||
| but when put in specific environment, behaves in specific way. Ok, I know, it's cryptic, | ||||
| but bear with me for a minute. Simply put, a stub is a dummy, which depending on the called | ||||
| method signature does different things (has logic). To create stubs in Prophecy: | ||||
|  | ||||
| ```php | ||||
| $prophecy->read('123')->willReturn('value'); | ||||
| ``` | ||||
|  | ||||
| Oh wow. We've just made an arbitrary call on the object prophecy? Yes, we did. And this | ||||
| call returned us a new object instance of class `MethodProphecy`. Yep, that's a specific | ||||
| method with arguments prophecy. Method prophecies give you the ability to create method | ||||
| promises or predictions. We'll talk about method predictions later in the _Mocks_ section. | ||||
|  | ||||
| #### Promises | ||||
|  | ||||
| Promises are logical blocks, that represent your fictional methods in prophecy terms | ||||
| and they are handled by the `MethodProphecy::will(PromiseInterface $promise)` method. | ||||
| As a matter of fact, the call that we made earlier (`willReturn('value')`) is a simple | ||||
| shortcut to: | ||||
|  | ||||
| ```php | ||||
| $prophecy->read('123')->will(new Prophecy\Promise\ReturnPromise(array('value'))); | ||||
| ``` | ||||
|  | ||||
| This promise will cause any call to our double's `read()` method with exactly one | ||||
| argument - `'123'` to always return `'value'`. But that's only for this | ||||
| promise, there's plenty others you can use: | ||||
|  | ||||
| - `ReturnPromise` or `->willReturn(1)` - returns a value from a method call | ||||
| - `ReturnArgumentPromise` or `->willReturnArgument($index)` - returns the nth method argument from call | ||||
| - `ThrowPromise` or `->willThrow` - causes the method to throw specific exception | ||||
| - `CallbackPromise` or `->will($callback)` - gives you a quick way to define your own custom logic | ||||
|  | ||||
| Keep in mind, that you can always add even more promises by implementing | ||||
| `Prophecy\Promise\PromiseInterface`. | ||||
|  | ||||
| #### Method prophecies idempotency | ||||
|  | ||||
| Prophecy enforces same method prophecies and, as a consequence, same promises and | ||||
| predictions for the same method calls with the same arguments. This means: | ||||
|  | ||||
| ```php | ||||
| $methodProphecy1 = $prophecy->read('123'); | ||||
| $methodProphecy2 = $prophecy->read('123'); | ||||
| $methodProphecy3 = $prophecy->read('321'); | ||||
|  | ||||
| $methodProphecy1 === $methodProphecy2; | ||||
| $methodProphecy1 !== $methodProphecy3; | ||||
| ``` | ||||
|  | ||||
| That's interesting, right? Now you might ask me how would you define more complex | ||||
| behaviors where some method call changes behavior of others. In PHPUnit or Mockery | ||||
| you do that by predicting how many times your method will be called. In Prophecy, | ||||
| you'll use promises for that: | ||||
|  | ||||
| ```php | ||||
| $user->getName()->willReturn(null); | ||||
|  | ||||
| // For PHP 5.4 | ||||
| $user->setName('everzet')->will(function () { | ||||
|     $this->getName()->willReturn('everzet'); | ||||
| }); | ||||
|  | ||||
| // For PHP 5.3 | ||||
| $user->setName('everzet')->will(function ($args, $user) { | ||||
|     $user->getName()->willReturn('everzet'); | ||||
| }); | ||||
|  | ||||
| // Or | ||||
| $user->setName('everzet')->will(function ($args) use ($user) { | ||||
|     $user->getName()->willReturn('everzet'); | ||||
| }); | ||||
| ``` | ||||
|  | ||||
| And now it doesn't matter how many times or in which order your methods are called. | ||||
| What matters is their behaviors and how well you faked it. | ||||
|  | ||||
| #### Arguments wildcarding | ||||
|  | ||||
| The previous example is awesome (at least I hope it is for you), but that's not | ||||
| optimal enough. We hardcoded `'everzet'` in our expectation. Isn't there a better | ||||
| way? In fact there is, but it involves understanding what this `'everzet'` | ||||
| actually is. | ||||
|  | ||||
| You see, even if method arguments used during method prophecy creation look | ||||
| like simple method arguments, in reality they are not. They are argument token | ||||
| wildcards.  As a matter of fact, `->setName('everzet')` looks like a simple call just | ||||
| because Prophecy automatically transforms it under the hood into: | ||||
|  | ||||
| ```php | ||||
| $user->setName(new Prophecy\Argument\Token\ExactValueToken('everzet')); | ||||
| ``` | ||||
|  | ||||
| Those argument tokens are simple PHP classes, that implement | ||||
| `Prophecy\Argument\Token\TokenInterface` and tell Prophecy how to compare real arguments | ||||
| with your expectations. And yes, those classnames are damn big. That's why there's a | ||||
| shortcut class `Prophecy\Argument`, which you can use to create tokens like that: | ||||
|  | ||||
| ```php | ||||
| use Prophecy\Argument; | ||||
|  | ||||
| $user->setName(Argument::exact('everzet')); | ||||
| ``` | ||||
|  | ||||
| `ExactValueToken` is not very useful in our case as it forced us to hardcode the username. | ||||
| That's why Prophecy comes bundled with a bunch of other tokens: | ||||
|  | ||||
| - `IdenticalValueToken` or `Argument::is($value)` - checks that the argument is identical to a specific value | ||||
| - `ExactValueToken` or `Argument::exact($value)` - checks that the argument matches a specific value | ||||
| - `TypeToken` or `Argument::type($typeOrClass)` - checks that the argument matches a specific type or | ||||
|   classname | ||||
| - `ObjectStateToken` or `Argument::which($method, $value)` - checks that the argument method returns | ||||
|   a specific value | ||||
| - `CallbackToken` or `Argument::that(callback)` - checks that the argument matches a custom callback | ||||
| - `AnyValueToken` or `Argument::any()` - matches any argument | ||||
| - `AnyValuesToken` or `Argument::cetera()` - matches any arguments to the rest of the signature | ||||
|  | ||||
| And you can add even more by implementing `TokenInterface` with your own custom classes. | ||||
|  | ||||
| So, let's refactor our initial `{set,get}Name()` logic with argument tokens: | ||||
|  | ||||
| ```php | ||||
| use Prophecy\Argument; | ||||
|  | ||||
| $user->getName()->willReturn(null); | ||||
|  | ||||
| // For PHP 5.4 | ||||
| $user->setName(Argument::type('string'))->will(function ($args) { | ||||
|     $this->getName()->willReturn($args[0]); | ||||
| }); | ||||
|  | ||||
| // For PHP 5.3 | ||||
| $user->setName(Argument::type('string'))->will(function ($args, $user) { | ||||
|     $user->getName()->willReturn($args[0]); | ||||
| }); | ||||
|  | ||||
| // Or | ||||
| $user->setName(Argument::type('string'))->will(function ($args) use ($user) { | ||||
|     $user->getName()->willReturn($args[0]); | ||||
| }); | ||||
| ``` | ||||
|  | ||||
| That's it. Now our `{set,get}Name()` prophecy will work with any string argument provided to it. | ||||
| We've just described how our stub object should behave, even though the original object could have | ||||
| no behavior whatsoever. | ||||
|  | ||||
| One last bit about arguments now. You might ask, what happens in case of: | ||||
|  | ||||
| ```php | ||||
| use Prophecy\Argument; | ||||
|  | ||||
| $user->getName()->willReturn(null); | ||||
|  | ||||
| // For PHP 5.4 | ||||
| $user->setName(Argument::type('string'))->will(function ($args) { | ||||
|     $this->getName()->willReturn($args[0]); | ||||
| }); | ||||
|  | ||||
| // For PHP 5.3 | ||||
| $user->setName(Argument::type('string'))->will(function ($args, $user) { | ||||
|     $user->getName()->willReturn($args[0]); | ||||
| }); | ||||
|  | ||||
| // Or | ||||
| $user->setName(Argument::type('string'))->will(function ($args) use ($user) { | ||||
|     $user->getName()->willReturn($args[0]); | ||||
| }); | ||||
|  | ||||
| $user->setName(Argument::any())->will(function () { | ||||
| }); | ||||
| ``` | ||||
|  | ||||
| Nothing. Your stub will continue behaving the way it did before. That's because of how | ||||
| arguments wildcarding works. Every argument token type has a different score level, which | ||||
| wildcard then uses to calculate the final arguments match score and use the method prophecy | ||||
| promise that has the highest score. In this case, `Argument::type()` in case of success | ||||
| scores `5` and `Argument::any()` scores `3`. So the type token wins, as does the first | ||||
| `setName()` method prophecy and its promise. The simple rule of thumb - more precise token | ||||
| always wins. | ||||
|  | ||||
| #### Getting stub objects | ||||
|  | ||||
| Ok, now we know how to define our prophecy method promises, let's get our stub from | ||||
| it: | ||||
|  | ||||
| ```php | ||||
| $stub = $prophecy->reveal(); | ||||
| ``` | ||||
|  | ||||
| As you might see, the only difference between how we get dummies and stubs is that with | ||||
| stubs we describe every object conversation instead of just agreeing with `null` returns | ||||
| (object being *dummy*). As a matter of fact, after you define your first promise | ||||
| (method call), Prophecy will force you to define all the communications - it throws | ||||
| the `UnexpectedCallException` for any call you didn't describe with object prophecy before | ||||
| calling it on a stub. | ||||
|  | ||||
| ### Mocks | ||||
|  | ||||
| Now we know how to define doubles without behavior (dummies) and doubles with behavior, but | ||||
| no expectations (stubs). What's left is doubles for which we have some expectations. These | ||||
| are called mocks and in Prophecy they look almost exactly the same as stubs, except that | ||||
| they define *predictions* instead of *promises* on method prophecies: | ||||
|  | ||||
| ```php | ||||
| $entityManager->flush()->shouldBeCalled(); | ||||
| ``` | ||||
|  | ||||
| #### Predictions | ||||
|  | ||||
| The `shouldBeCalled()` method here assigns `CallPrediction` to our method prophecy. | ||||
| Predictions are a delayed behavior check for your prophecies. You see, during the entire lifetime | ||||
| of your doubles, Prophecy records every single call you're making against it inside your | ||||
| code. After that, Prophecy can use this collected information to check if it matches defined | ||||
| predictions. You can assign predictions to method prophecies using the | ||||
| `MethodProphecy::should(PredictionInterface $prediction)` method. As a matter of fact, | ||||
| the `shouldBeCalled()` method we used earlier is just a shortcut to: | ||||
|  | ||||
| ```php | ||||
| $entityManager->flush()->should(new Prophecy\Prediction\CallPrediction()); | ||||
| ``` | ||||
|  | ||||
| It checks if your method of interest (that matches both the method name and the arguments wildcard) | ||||
| was called 1 or more times. If the prediction failed then it throws an exception. When does this | ||||
| check happen? Whenever you call `checkPredictions()` on the main Prophet object: | ||||
|  | ||||
| ```php | ||||
| $prophet->checkPredictions(); | ||||
| ``` | ||||
|  | ||||
| In PHPUnit, you would want to put this call into the `tearDown()` method. If no predictions | ||||
| are defined, it would do nothing. So it won't harm to call it after every test. | ||||
|  | ||||
| There are plenty more predictions you can play with: | ||||
|  | ||||
| - `CallPrediction` or `shouldBeCalled()` - checks that the method has been called 1 or more times | ||||
| - `NoCallsPrediction` or `shouldNotBeCalled()` - checks that the method has not been called | ||||
| - `CallTimesPrediction` or `shouldBeCalledTimes($count)` - checks that the method has been called | ||||
|   `$count` times | ||||
| - `CallbackPrediction` or `should($callback)` - checks the method against your own custom callback | ||||
|  | ||||
| Of course, you can always create your own custom prediction any time by implementing | ||||
| `PredictionInterface`. | ||||
|  | ||||
| ### Spies | ||||
|  | ||||
| The last bit of awesomeness in Prophecy is out-of-the-box spies support. As I said in the previous | ||||
| section, Prophecy records every call made during the double's entire lifetime. This means | ||||
| you don't need to record predictions in order to check them. You can also do it | ||||
| manually by using the `MethodProphecy::shouldHave(PredictionInterface $prediction)` method: | ||||
|  | ||||
| ```php | ||||
| $em = $prophet->prophesize('Doctrine\ORM\EntityManager'); | ||||
|  | ||||
| $controller->createUser($em->reveal()); | ||||
|  | ||||
| $em->flush()->shouldHaveBeenCalled(); | ||||
| ``` | ||||
|  | ||||
| Such manipulation with doubles is called spying. And with Prophecy it just works. | ||||
							
								
								
									
										40
									
								
								vendor/phpspec/prophecy/composer.json
									
									
									
									
										vendored
									
									
								
							
							
						
						
									
										40
									
								
								vendor/phpspec/prophecy/composer.json
									
									
									
									
										vendored
									
									
								
							| @@ -1,40 +0,0 @@ | ||||
| { | ||||
|     "name":         "phpspec/prophecy", | ||||
|     "description":  "Highly opinionated mocking framework for PHP 5.3+", | ||||
|     "keywords":     ["Mock", "Stub", "Dummy", "Double", "Fake", "Spy"], | ||||
|     "homepage":     "https://github.com/phpspec/prophecy", | ||||
|     "type":         "library", | ||||
|     "license":      "MIT", | ||||
|     "authors":      [ | ||||
|         { | ||||
|             "name":      "Konstantin Kudryashov", | ||||
|             "email":     "ever.zet@gmail.com", | ||||
|             "homepage":  "http://everzet.com" | ||||
|         }, | ||||
|         { | ||||
|             "name":      "Marcello Duarte", | ||||
|             "email":     "marcello.duarte@gmail.com" | ||||
|         } | ||||
|     ], | ||||
|     "require": { | ||||
|         "phpdocumentor/reflection-docblock": "~2.0", | ||||
|         "sebastian/comparator":              "~1.1", | ||||
|         "doctrine/instantiator":             "^1.0.2" | ||||
|     }, | ||||
|  | ||||
|     "require-dev": { | ||||
|         "phpspec/phpspec": "~2.0" | ||||
|     }, | ||||
|  | ||||
|     "autoload": { | ||||
|         "psr-0": { | ||||
|             "Prophecy\\": "src/" | ||||
|         } | ||||
|     }, | ||||
|  | ||||
|     "extra": { | ||||
|         "branch-alias": { | ||||
|             "dev-master": "1.4.x-dev" | ||||
|         } | ||||
|     } | ||||
| } | ||||
| @@ -1,143 +0,0 @@ | ||||
| <?php | ||||
|  | ||||
| namespace spec\Prophecy\Argument; | ||||
|  | ||||
| use PhpSpec\ObjectBehavior; | ||||
| use Prophecy\Argument\Token\TokenInterface; | ||||
|  | ||||
| class ArgumentsWildcardSpec extends ObjectBehavior | ||||
| { | ||||
|     /** | ||||
|      * @param \stdClass $object | ||||
|      */ | ||||
|     function it_wraps_non_token_arguments_into_ExactValueToken($object) | ||||
|     { | ||||
|         $this->beConstructedWith(array(42, 'zet', $object)); | ||||
|  | ||||
|         $class = get_class($object->getWrappedObject()); | ||||
|         $hash  = spl_object_hash($object->getWrappedObject()); | ||||
|  | ||||
|         $this->__toString()->shouldReturn("exact(42), exact(\"zet\"), exact($class:$hash Object (\n    'objectProphecy' => Prophecy\Prophecy\ObjectProphecy Object (*Prophecy*)\n))"); | ||||
|     } | ||||
|  | ||||
|     /** | ||||
|      * @param \Prophecy\Argument\Token\TokenInterface $token1 | ||||
|      * @param \Prophecy\Argument\Token\TokenInterface $token2 | ||||
|      * @param \Prophecy\Argument\Token\TokenInterface $token3 | ||||
|      */ | ||||
|     function it_generates_string_representation_from_all_tokens_imploded($token1, $token2, $token3) | ||||
|     { | ||||
|         $token1->__toString()->willReturn('token_1'); | ||||
|         $token2->__toString()->willReturn('token_2'); | ||||
|         $token3->__toString()->willReturn('token_3'); | ||||
|  | ||||
|         $this->beConstructedWith(array($token1, $token2, $token3)); | ||||
|         $this->__toString()->shouldReturn('token_1, token_2, token_3'); | ||||
|     } | ||||
|  | ||||
|     function it_exposes_list_of_tokens(TokenInterface $token) | ||||
|     { | ||||
|         $this->beConstructedWith(array($token)); | ||||
|  | ||||
|         $this->getTokens()->shouldReturn(array($token)); | ||||
|     } | ||||
|  | ||||
|     function it_returns_score_of_1_if_there_are_no_tokens_and_arguments() | ||||
|     { | ||||
|         $this->beConstructedWith(array()); | ||||
|  | ||||
|         $this->scoreArguments(array())->shouldReturn(1); | ||||
|     } | ||||
|  | ||||
|     /** | ||||
|      * @param \Prophecy\Argument\Token\TokenInterface $token1 | ||||
|      * @param \Prophecy\Argument\Token\TokenInterface $token2 | ||||
|      * @param \Prophecy\Argument\Token\TokenInterface $token3 | ||||
|      */ | ||||
|     function it_should_return_match_score_based_on_all_tokens_score($token1, $token2, $token3) | ||||
|     { | ||||
|         $token1->scoreArgument('one')->willReturn(3); | ||||
|         $token1->isLast()->willReturn(false); | ||||
|         $token2->scoreArgument(2)->willReturn(5); | ||||
|         $token2->isLast()->willReturn(false); | ||||
|         $token3->scoreArgument($obj = new \stdClass())->willReturn(10); | ||||
|         $token3->isLast()->willReturn(false); | ||||
|  | ||||
|         $this->beConstructedWith(array($token1, $token2, $token3)); | ||||
|         $this->scoreArguments(array('one', 2, $obj))->shouldReturn(18); | ||||
|     } | ||||
|  | ||||
|     /** | ||||
|      * @param \Prophecy\Argument\Token\TokenInterface $token1 | ||||
|      * @param \Prophecy\Argument\Token\TokenInterface $token2 | ||||
|      * @param \Prophecy\Argument\Token\TokenInterface $token3 | ||||
|      */ | ||||
|     function it_returns_false_if_there_is_less_arguments_than_tokens($token1, $token2, $token3) | ||||
|     { | ||||
|         $token1->scoreArgument('one')->willReturn(3); | ||||
|         $token1->isLast()->willReturn(false); | ||||
|         $token2->scoreArgument(2)->willReturn(5); | ||||
|         $token2->isLast()->willReturn(false); | ||||
|         $token3->scoreArgument(null)->willReturn(false); | ||||
|         $token3->isLast()->willReturn(false); | ||||
|  | ||||
|         $this->beConstructedWith(array($token1, $token2, $token3)); | ||||
|         $this->scoreArguments(array('one', 2))->shouldReturn(false); | ||||
|     } | ||||
|  | ||||
|     /** | ||||
|      * @param \Prophecy\Argument\Token\TokenInterface $token1 | ||||
|      * @param \Prophecy\Argument\Token\TokenInterface $token2 | ||||
|      * @param \Prophecy\Argument\Token\TokenInterface $token3 | ||||
|      */ | ||||
|     function it_returns_false_if_there_is_less_tokens_than_arguments($token1, $token2, $token3) | ||||
|     { | ||||
|         $token1->scoreArgument('one')->willReturn(3); | ||||
|         $token1->isLast()->willReturn(false); | ||||
|         $token2->scoreArgument(2)->willReturn(5); | ||||
|         $token2->isLast()->willReturn(false); | ||||
|         $token3->scoreArgument($obj = new \stdClass())->willReturn(10); | ||||
|         $token3->isLast()->willReturn(false); | ||||
|  | ||||
|         $this->beConstructedWith(array($token1, $token2, $token3)); | ||||
|         $this->scoreArguments(array('one', 2, $obj, 4))->shouldReturn(false); | ||||
|     } | ||||
|  | ||||
|     /** | ||||
|      * @param \Prophecy\Argument\Token\TokenInterface $token1 | ||||
|      * @param \Prophecy\Argument\Token\TokenInterface $token2 | ||||
|      * @param \Prophecy\Argument\Token\TokenInterface $token3 | ||||
|      */ | ||||
|     function it_should_return_false_if_one_of_the_tokens_returns_false($token1, $token2, $token3) | ||||
|     { | ||||
|         $token1->scoreArgument('one')->willReturn(3); | ||||
|         $token1->isLast()->willReturn(false); | ||||
|         $token2->scoreArgument(2)->willReturn(false); | ||||
|         $token2->isLast()->willReturn(false); | ||||
|         $token3->scoreArgument($obj = new \stdClass())->willReturn(10); | ||||
|         $token3->isLast()->willReturn(false); | ||||
|  | ||||
|         $this->beConstructedWith(array($token1, $token2, $token3)); | ||||
|         $this->scoreArguments(array('one', 2, $obj))->shouldReturn(false); | ||||
|     } | ||||
|  | ||||
|     /** | ||||
|      * @param \Prophecy\Argument\Token\TokenInterface $token1 | ||||
|      * @param \Prophecy\Argument\Token\TokenInterface $token2 | ||||
|      * @param \Prophecy\Argument\Token\TokenInterface $token3 | ||||
|      */ | ||||
|     function it_should_calculate_score_until_last_token($token1, $token2, $token3) | ||||
|     { | ||||
|         $token1->scoreArgument('one')->willReturn(3); | ||||
|         $token1->isLast()->willReturn(false); | ||||
|  | ||||
|         $token2->scoreArgument(2)->willReturn(7); | ||||
|         $token2->isLast()->willReturn(true); | ||||
|  | ||||
|         $token3->scoreArgument($obj = new \stdClass())->willReturn(10); | ||||
|         $token3->isLast()->willReturn(false); | ||||
|  | ||||
|         $this->beConstructedWith(array($token1, $token2, $token3)); | ||||
|         $this->scoreArguments(array('one', 2, $obj))->shouldReturn(10); | ||||
|     } | ||||
| } | ||||
| @@ -1,28 +0,0 @@ | ||||
| <?php | ||||
|  | ||||
| namespace spec\Prophecy\Argument\Token; | ||||
|  | ||||
| use PhpSpec\ObjectBehavior; | ||||
|  | ||||
| class AnyValueTokenSpec extends ObjectBehavior | ||||
| { | ||||
|     function it_implements_TokenInterface() | ||||
|     { | ||||
|         $this->shouldBeAnInstanceOf('Prophecy\Argument\Token\TokenInterface'); | ||||
|     } | ||||
|  | ||||
|     function it_is_not_last() | ||||
|     { | ||||
|         $this->shouldNotBeLast(); | ||||
|     } | ||||
|  | ||||
|     function its_string_representation_is_star() | ||||
|     { | ||||
|         $this->__toString()->shouldReturn('*'); | ||||
|     } | ||||
|  | ||||
|     function it_scores_any_argument_as_3() | ||||
|     { | ||||
|         $this->scoreArgument(42)->shouldReturn(3); | ||||
|     } | ||||
| } | ||||
| @@ -1,28 +0,0 @@ | ||||
| <?php | ||||
|  | ||||
| namespace spec\Prophecy\Argument\Token; | ||||
|  | ||||
| use PhpSpec\ObjectBehavior; | ||||
|  | ||||
| class AnyValuesTokenSpec extends ObjectBehavior | ||||
| { | ||||
|     function it_implements_TokenInterface() | ||||
|     { | ||||
|         $this->shouldBeAnInstanceOf('Prophecy\Argument\Token\TokenInterface'); | ||||
|     } | ||||
|  | ||||
|     function it_is_last() | ||||
|     { | ||||
|         $this->shouldBeLast(); | ||||
|     } | ||||
|  | ||||
|     function its_string_representation_is_star_with_followup() | ||||
|     { | ||||
|         $this->__toString()->shouldReturn('* [, ...]'); | ||||
|     } | ||||
|  | ||||
|     function it_scores_any_argument_as_2() | ||||
|     { | ||||
|         $this->scoreArgument(42)->shouldReturn(2); | ||||
|     } | ||||
| } | ||||
| @@ -1,64 +0,0 @@ | ||||
| <?php | ||||
|  | ||||
| namespace spec\Prophecy\Argument\Token; | ||||
|  | ||||
| use PhpSpec\ObjectBehavior; | ||||
|  | ||||
| class ArrayCountTokenSpec extends ObjectBehavior | ||||
| { | ||||
|     function let() | ||||
|     { | ||||
|         $this->beConstructedWith(2); | ||||
|     } | ||||
|  | ||||
|     function it_implements_TokenInterface() | ||||
|     { | ||||
|         $this->shouldBeAnInstanceOf('Prophecy\Argument\Token\TokenInterface'); | ||||
|     } | ||||
|  | ||||
|     function it_is_not_last() | ||||
|     { | ||||
|         $this->shouldNotBeLast(); | ||||
|     } | ||||
|  | ||||
|     function it_scores_6_if_argument_array_has_proper_count() | ||||
|     { | ||||
|         $this->scoreArgument(array(1,2))->shouldReturn(6); | ||||
|     } | ||||
|  | ||||
|     /** | ||||
|      * @param \Countable $countable | ||||
|      */ | ||||
|     function it_scores_6_if_argument_countable_object_has_proper_count($countable) | ||||
|     { | ||||
|         $countable->count()->willReturn(2); | ||||
|         $this->scoreArgument($countable)->shouldReturn(6); | ||||
|     } | ||||
|  | ||||
|     function it_does_not_score_if_argument_is_neither_array_nor_countable_object() | ||||
|     { | ||||
|         $this->scoreArgument('string')->shouldBe(false); | ||||
|         $this->scoreArgument(5)->shouldBe(false); | ||||
|         $this->scoreArgument(new \stdClass)->shouldBe(false); | ||||
|     } | ||||
|  | ||||
|     function it_does_not_score_if_argument_array_has_wrong_count() | ||||
|     { | ||||
|         $this->scoreArgument(array(1))->shouldReturn(false); | ||||
|     } | ||||
|  | ||||
|     /** | ||||
|      * @param \Countable $countable | ||||
|      */ | ||||
|     function it_does_not_score_if_argument_countable_object_has_wrong_count($countable) | ||||
|     { | ||||
|         $countable->count()->willReturn(3); | ||||
|         $this->scoreArgument($countable)->shouldReturn(false); | ||||
|     } | ||||
|  | ||||
|     function it_has_simple_string_representation() | ||||
|     { | ||||
|         $this->__toString()->shouldBe('count(2)'); | ||||
|     } | ||||
|  | ||||
| } | ||||
| @@ -1,229 +0,0 @@ | ||||
| <?php | ||||
|  | ||||
| namespace spec\Prophecy\Argument\Token; | ||||
|  | ||||
| use PhpSpec\ObjectBehavior; | ||||
| use Prophecy\Argument; | ||||
| use Prophecy\Exception\InvalidArgumentException; | ||||
|  | ||||
| class ArrayEntryTokenSpec extends ObjectBehavior | ||||
| { | ||||
|     /** | ||||
|      * @param \Prophecy\Argument\Token\TokenInterface $key | ||||
|      * @param \Prophecy\Argument\Token\TokenInterface $value | ||||
|      */ | ||||
|     function let($key, $value) | ||||
|     { | ||||
|         $this->beConstructedWith($key, $value); | ||||
|     } | ||||
|  | ||||
|     function it_implements_TokenInterface() | ||||
|     { | ||||
|         $this->shouldBeAnInstanceOf('Prophecy\Argument\Token\TokenInterface'); | ||||
|     } | ||||
|  | ||||
|     function it_is_not_last() | ||||
|     { | ||||
|         $this->shouldNotBeLast(); | ||||
|     } | ||||
|  | ||||
|     function it_holds_key_and_value($key, $value) | ||||
|     { | ||||
|         $this->getKey()->shouldBe($key); | ||||
|         $this->getValue()->shouldBe($value); | ||||
|     } | ||||
|  | ||||
|     function its_string_representation_tells_that_its_an_array_containing_the_key_value_pair($key, $value) | ||||
|     { | ||||
|         $key->__toString()->willReturn('key'); | ||||
|         $value->__toString()->willReturn('value'); | ||||
|         $this->__toString()->shouldBe('[..., key => value, ...]'); | ||||
|     } | ||||
|  | ||||
|     /** | ||||
|      * @param \Prophecy\Argument\Token\TokenInterface $key | ||||
|      * @param \stdClass                               $object | ||||
|      */ | ||||
|     function it_wraps_non_token_value_into_ExactValueToken($key, $object) | ||||
|     { | ||||
|         $this->beConstructedWith($key, $object); | ||||
|         $this->getValue()->shouldHaveType('\Prophecy\Argument\Token\ExactValueToken'); | ||||
|     } | ||||
|  | ||||
|     /** | ||||
|      * @param \stdClass                               $object | ||||
|      * @param \Prophecy\Argument\Token\TokenInterface $value | ||||
|      */ | ||||
|     function it_wraps_non_token_key_into_ExactValueToken($object, $value) | ||||
|     { | ||||
|         $this->beConstructedWith($object, $value); | ||||
|         $this->getKey()->shouldHaveType('\Prophecy\Argument\Token\ExactValueToken'); | ||||
|     } | ||||
|  | ||||
|     function it_scores_array_half_of_combined_scores_from_key_and_value_tokens($key, $value) | ||||
|     { | ||||
|         $key->scoreArgument('key')->willReturn(4); | ||||
|         $value->scoreArgument('value')->willReturn(6); | ||||
|         $this->scoreArgument(array('key'=>'value'))->shouldBe(5); | ||||
|     } | ||||
|  | ||||
|     /** | ||||
|      * @param \Prophecy\Argument\Token\TokenInterface $key | ||||
|      * @param \Prophecy\Argument\Token\TokenInterface $value | ||||
|      * @param \Iterator                               $object | ||||
|      */ | ||||
|     function it_scores_traversable_object_half_of_combined_scores_from_key_and_value_tokens($key, $value, $object) | ||||
|     { | ||||
|         $object->current()->will(function () use ($object) { | ||||
|             $object->valid()->willReturn(false); | ||||
|  | ||||
|             return 'value'; | ||||
|         }); | ||||
|         $object->key()->willReturn('key'); | ||||
|         $object->rewind()->willReturn(null); | ||||
|         $object->next()->willReturn(null); | ||||
|         $object->valid()->willReturn(true); | ||||
|         $key->scoreArgument('key')->willReturn(6); | ||||
|         $value->scoreArgument('value')->willReturn(2); | ||||
|         $this->scoreArgument($object)->shouldBe(4); | ||||
|     } | ||||
|  | ||||
|     /** | ||||
|      * @param \Prophecy\Argument\Token\AnyValuesToken $key | ||||
|      * @param \Prophecy\Argument\Token\TokenInterface $value | ||||
|      * @param \ArrayAccess                            $object | ||||
|      */ | ||||
|     function it_throws_exception_during_scoring_of_array_accessible_object_if_key_is_not_ExactValueToken($key, $value, $object) | ||||
|     { | ||||
|         $key->__toString()->willReturn('any_token'); | ||||
|         $this->beConstructedWith($key,$value); | ||||
|         $errorMessage = 'You can only use exact value tokens to match key of ArrayAccess object'.PHP_EOL. | ||||
|                         'But you used `any_token`.'; | ||||
|         $this->shouldThrow(new InvalidArgumentException($errorMessage))->duringScoreArgument($object); | ||||
|     } | ||||
|  | ||||
|     /** | ||||
|      * @param \Prophecy\Argument\Token\ExactValueToken $key | ||||
|      * @param \Prophecy\Argument\Token\TokenInterface  $value | ||||
|      * @param \ArrayAccess                             $object | ||||
|      */ | ||||
|     function it_scores_array_accessible_object_half_of_combined_scores_from_key_and_value_tokens($key, $value, $object) | ||||
|     { | ||||
|         $object->offsetExists('key')->willReturn(true); | ||||
|         $object->offsetGet('key')->willReturn('value'); | ||||
|         $key->getValue()->willReturn('key'); | ||||
|         $key->scoreArgument('key')->willReturn(3); | ||||
|         $value->scoreArgument('value')->willReturn(1); | ||||
|         $this->scoreArgument($object)->shouldBe(2); | ||||
|     } | ||||
|  | ||||
|     /** | ||||
|      * @param \Prophecy\Argument\Token\AnyValuesToken $key | ||||
|      * @param \Prophecy\Argument\Token\TokenInterface $value | ||||
|      * @param \ArrayIterator                          $object | ||||
|      */ | ||||
|     function it_accepts_any_key_token_type_to_score_object_that_is_both_traversable_and_array_accessible($key, $value, $object) | ||||
|     { | ||||
|         $this->beConstructedWith($key, $value); | ||||
|         $object->current()->will(function () use ($object) { | ||||
|             $object->valid()->willReturn(false); | ||||
|  | ||||
|             return 'value'; | ||||
|         }); | ||||
|         $object->key()->willReturn('key'); | ||||
|         $object->rewind()->willReturn(null); | ||||
|         $object->next()->willReturn(null); | ||||
|         $object->valid()->willReturn(true); | ||||
|         $this->shouldNotThrow(new InvalidArgumentException)->duringScoreArgument($object); | ||||
|     } | ||||
|  | ||||
|     function it_does_not_score_if_argument_is_neither_array_nor_traversable_nor_array_accessible() | ||||
|     { | ||||
|         $this->scoreArgument('string')->shouldBe(false); | ||||
|         $this->scoreArgument(new \stdClass)->shouldBe(false); | ||||
|     } | ||||
|  | ||||
|     function it_does_not_score_empty_array() | ||||
|     { | ||||
|         $this->scoreArgument(array())->shouldBe(false); | ||||
|     } | ||||
|  | ||||
|     function it_does_not_score_array_if_key_and_value_tokens_do_not_score_same_entry($key, $value) | ||||
|     { | ||||
|         $argument = array(1 => 'foo', 2 => 'bar'); | ||||
|         $key->scoreArgument(1)->willReturn(true); | ||||
|         $key->scoreArgument(2)->willReturn(false); | ||||
|         $value->scoreArgument('foo')->willReturn(false); | ||||
|         $value->scoreArgument('bar')->willReturn(true); | ||||
|         $this->scoreArgument($argument)->shouldBe(false); | ||||
|     } | ||||
|  | ||||
|     /** | ||||
|      * @param \Iterator $object | ||||
|      */ | ||||
|     function it_does_not_score_traversable_object_without_entries($object) | ||||
|     { | ||||
|         $object->rewind()->willReturn(null); | ||||
|         $object->next()->willReturn(null); | ||||
|         $object->valid()->willReturn(false); | ||||
|         $this->scoreArgument($object)->shouldBe(false); | ||||
|     } | ||||
|  | ||||
|     /** | ||||
|      * @param \Prophecy\Argument\Token\TokenInterface $key | ||||
|      * @param \Prophecy\Argument\Token\TokenInterface $value | ||||
|      * @param \Iterator                               $object | ||||
|      */ | ||||
|     function it_does_not_score_traversable_object_if_key_and_value_tokens_do_not_score_same_entry($key, $value, $object) | ||||
|     { | ||||
|         $object->current()->willReturn('foo'); | ||||
|         $object->current()->will(function () use ($object) { | ||||
|             $object->valid()->willReturn(false); | ||||
|  | ||||
|             return 'bar'; | ||||
|         }); | ||||
|         $object->key()->willReturn(1); | ||||
|         $object->key()->willReturn(2); | ||||
|         $object->rewind()->willReturn(null); | ||||
|         $object->next()->willReturn(null); | ||||
|         $object->valid()->willReturn(true); | ||||
|         $key->scoreArgument(1)->willReturn(true); | ||||
|         $key->scoreArgument(2)->willReturn(false); | ||||
|         $value->scoreArgument('foo')->willReturn(false); | ||||
|         $value->scoreArgument('bar')->willReturn(true); | ||||
|         $this->scoreArgument($object)->shouldBe(false); | ||||
|     } | ||||
|  | ||||
|     /** | ||||
|      * @param \Prophecy\Argument\Token\ExactValueToken $key | ||||
|      * @param \ArrayAccess                             $object | ||||
|      */ | ||||
|     function it_does_not_score_array_accessible_object_if_it_has_no_offset_with_key_token_value($key, $object) | ||||
|     { | ||||
|         $object->offsetExists('key')->willReturn(false); | ||||
|         $key->getValue()->willReturn('key'); | ||||
|         $this->scoreArgument($object)->shouldBe(false); | ||||
|     } | ||||
|  | ||||
|     /** | ||||
|      * @param \Prophecy\Argument\Token\ExactValueToken $key | ||||
|      * @param \Prophecy\Argument\Token\TokenInterface  $value | ||||
|      * @param \ArrayAccess                             $object | ||||
|      */ | ||||
|     function it_does_not_score_array_accessible_object_if_key_and_value_tokens_do_not_score_same_entry($key, $value, $object) | ||||
|     { | ||||
|         $object->offsetExists('key')->willReturn(true); | ||||
|         $object->offsetGet('key')->willReturn('value'); | ||||
|         $key->getValue()->willReturn('key'); | ||||
|         $value->scoreArgument('value')->willReturn(false); | ||||
|         $key->scoreArgument('key')->willReturn(true); | ||||
|         $this->scoreArgument($object)->shouldBe(false); | ||||
|     } | ||||
|  | ||||
|     function its_score_is_capped_at_8($key, $value) | ||||
|     { | ||||
|         $key->scoreArgument('key')->willReturn(10); | ||||
|         $value->scoreArgument('value')->willReturn(10); | ||||
|         $this->scoreArgument(array('key'=>'value'))->shouldBe(8); | ||||
|     } | ||||
| } | ||||
| @@ -1,109 +0,0 @@ | ||||
| <?php | ||||
|  | ||||
| namespace spec\Prophecy\Argument\Token; | ||||
|  | ||||
| use PhpSpec\ObjectBehavior; | ||||
| use Prophecy\Argument; | ||||
|  | ||||
| class ArrayEveryEntryTokenSpec extends ObjectBehavior | ||||
| { | ||||
|     /** | ||||
|      * @param \Prophecy\Argument\Token\TokenInterface $value | ||||
|      */ | ||||
|     function let($value) | ||||
|     { | ||||
|         $this->beConstructedWith($value); | ||||
|     } | ||||
|  | ||||
|     function it_implements_TokenInterface() | ||||
|     { | ||||
|         $this->shouldBeAnInstanceOf('Prophecy\Argument\Token\TokenInterface'); | ||||
|     } | ||||
|  | ||||
|     function it_is_not_last() | ||||
|     { | ||||
|         $this->shouldNotBeLast(); | ||||
|     } | ||||
|  | ||||
|     function it_holds_value($value) | ||||
|     { | ||||
|         $this->getValue()->shouldBe($value); | ||||
|     } | ||||
|  | ||||
|     function its_string_representation_tells_that_its_an_array_containing_only_value($value) | ||||
|     { | ||||
|         $value->__toString()->willReturn('value'); | ||||
|         $this->__toString()->shouldBe('[value, ..., value]'); | ||||
|     } | ||||
|  | ||||
|     /** | ||||
|      * @param \stdClass $stdClass | ||||
|      */ | ||||
|     function it_wraps_non_token_value_into_ExactValueToken($stdClass) | ||||
|     { | ||||
|         $this->beConstructedWith($stdClass); | ||||
|         $this->getValue()->shouldHaveType('Prophecy\Argument\Token\ExactValueToken'); | ||||
|     } | ||||
|  | ||||
|     function it_does_not_score_if_argument_is_neither_array_nor_traversable() | ||||
|     { | ||||
|         $this->scoreArgument('string')->shouldBe(false); | ||||
|         $this->scoreArgument(new \stdClass)->shouldBe(false); | ||||
|     } | ||||
|  | ||||
|     function it_does_not_score_empty_array() | ||||
|     { | ||||
|         $this->scoreArgument(array())->shouldBe(false); | ||||
|     } | ||||
|  | ||||
|     /** | ||||
|      * @param \Iterator $object | ||||
|      */ | ||||
|     function it_does_not_score_traversable_object_without_entries($object) | ||||
|     { | ||||
|         $object->rewind()->willReturn(null); | ||||
|         $object->next()->willReturn(null); | ||||
|         $object->valid()->willReturn(false); | ||||
|         $this->scoreArgument($object)->shouldBe(false); | ||||
|     } | ||||
|  | ||||
|     function it_scores_avg_of_scores_from_value_tokens($value) | ||||
|     { | ||||
|         $value->scoreArgument('value1')->willReturn(6); | ||||
|         $value->scoreArgument('value2')->willReturn(3); | ||||
|         $this->scoreArgument(array('value1', 'value2'))->shouldBe(4.5); | ||||
|     } | ||||
|  | ||||
|     function it_scores_false_if_entry_scores_false($value) | ||||
|     { | ||||
|         $value->scoreArgument('value1')->willReturn(6); | ||||
|         $value->scoreArgument('value2')->willReturn(false); | ||||
|         $this->scoreArgument(array('value1', 'value2'))->shouldBe(false); | ||||
|     } | ||||
|  | ||||
|     function it_does_not_score_array_keys($value) | ||||
|     { | ||||
|         $value->scoreArgument('value')->willReturn(6); | ||||
|         $value->scoreArgument('key')->shouldNotBeCalled(0); | ||||
|         $this->scoreArgument(array('key' => 'value'))->shouldBe(6); | ||||
|     } | ||||
|  | ||||
|     /** | ||||
|      * @param \Prophecy\Argument\Token\TokenInterface $value | ||||
|      * @param \Iterator                               $object | ||||
|      */ | ||||
|     function it_scores_traversable_object_from_value_token($value, $object) | ||||
|     { | ||||
|         $object->current()->will(function ($args, $object) { | ||||
|             $object->valid()->willReturn(false); | ||||
|  | ||||
|             return 'value'; | ||||
|         }); | ||||
|         $object->key()->willReturn('key'); | ||||
|         $object->rewind()->willReturn(null); | ||||
|         $object->next()->willReturn(null); | ||||
|         $object->valid()->willReturn(true); | ||||
|         $value->scoreArgument('value')->willReturn(2); | ||||
|         $this->scoreArgument($object)->shouldBe(2); | ||||
|     } | ||||
| } | ||||
| @@ -1,42 +0,0 @@ | ||||
| <?php | ||||
|  | ||||
| namespace spec\Prophecy\Argument\Token; | ||||
|  | ||||
| use PhpSpec\ObjectBehavior; | ||||
|  | ||||
| class CallbackTokenSpec extends ObjectBehavior | ||||
| { | ||||
|     function let() | ||||
|     { | ||||
|         $this->beConstructedWith('get_class'); | ||||
|     } | ||||
|  | ||||
|     function it_implements_TokenInterface() | ||||
|     { | ||||
|         $this->shouldBeAnInstanceOf('Prophecy\Argument\Token\TokenInterface'); | ||||
|     } | ||||
|  | ||||
|     function it_is_not_last() | ||||
|     { | ||||
|         $this->shouldNotBeLast(); | ||||
|     } | ||||
|  | ||||
|     function it_scores_7_if_argument_matches_callback() | ||||
|     { | ||||
|         $this->beConstructedWith(function ($argument) { return 2 === $argument; }); | ||||
|  | ||||
|         $this->scoreArgument(2)->shouldReturn(7); | ||||
|     } | ||||
|  | ||||
|     function it_does_not_scores_if_argument_does_not_match_callback() | ||||
|     { | ||||
|         $this->beConstructedWith(function ($argument) { return 2 === $argument; }); | ||||
|  | ||||
|         $this->scoreArgument(5)->shouldReturn(false); | ||||
|     } | ||||
|  | ||||
|     function its_string_representation_should_tell_that_its_callback() | ||||
|     { | ||||
|         $this->__toString()->shouldReturn('callback()'); | ||||
|     } | ||||
| } | ||||
| @@ -1,155 +0,0 @@ | ||||
| <?php | ||||
|  | ||||
| namespace spec\Prophecy\Argument\Token; | ||||
|  | ||||
| use PhpSpec\ObjectBehavior; | ||||
|  | ||||
| class ExactValueTokenSpec extends ObjectBehavior | ||||
| { | ||||
|     function let() | ||||
|     { | ||||
|         $this->beConstructedWith(42); | ||||
|     } | ||||
|  | ||||
|     function it_implements_TokenInterface() | ||||
|     { | ||||
|         $this->shouldBeAnInstanceOf('Prophecy\Argument\Token\TokenInterface'); | ||||
|     } | ||||
|  | ||||
|     function it_is_not_last() | ||||
|     { | ||||
|         $this->shouldNotBeLast(); | ||||
|     } | ||||
|  | ||||
|     function it_holds_value() | ||||
|     { | ||||
|         $this->getValue()->shouldReturn(42); | ||||
|     } | ||||
|  | ||||
|     function it_scores_10_if_value_is_equal_to_argument() | ||||
|     { | ||||
|         $this->scoreArgument(42)->shouldReturn(10); | ||||
|         $this->scoreArgument('42')->shouldReturn(10); | ||||
|     } | ||||
|  | ||||
|     function it_scores_10_if_value_is_an_object_and_equal_to_argument() | ||||
|     { | ||||
|         $value = new \DateTime(); | ||||
|         $value2 = clone $value; | ||||
|  | ||||
|         $this->beConstructedWith($value); | ||||
|         $this->scoreArgument($value2)->shouldReturn(10); | ||||
|     } | ||||
|  | ||||
|     function it_does_not_scores_if_value_is_not_equal_to_argument() | ||||
|     { | ||||
|         $this->scoreArgument(50)->shouldReturn(false); | ||||
|         $this->scoreArgument(new \stdClass())->shouldReturn(false); | ||||
|     } | ||||
|  | ||||
|     function it_does_not_scores_if_value_an_object_and_is_not_equal_to_argument() | ||||
|     { | ||||
|         $value = new ExactValueTokenFixtureB('ABC'); | ||||
|         $value2 = new ExactValueTokenFixtureB('CBA'); | ||||
|  | ||||
|         $this->beConstructedWith($value); | ||||
|         $this->scoreArgument($value2)->shouldReturn(false); | ||||
|     } | ||||
|  | ||||
|     function it_does_not_scores_if_value_type_and_is_not_equal_to_argument() | ||||
|     { | ||||
|         $this->beConstructedWith(false); | ||||
|         $this->scoreArgument(0)->shouldReturn(false); | ||||
|     } | ||||
|  | ||||
|     function it_generates_proper_string_representation_for_integer() | ||||
|     { | ||||
|         $this->beConstructedWith(42); | ||||
|         $this->__toString()->shouldReturn('exact(42)'); | ||||
|     } | ||||
|  | ||||
|     function it_generates_proper_string_representation_for_string() | ||||
|     { | ||||
|         $this->beConstructedWith('some string'); | ||||
|         $this->__toString()->shouldReturn('exact("some string")'); | ||||
|     } | ||||
|  | ||||
|     function it_generates_single_line_representation_for_multiline_string() | ||||
|     { | ||||
|         $this->beConstructedWith("some\nstring"); | ||||
|         $this->__toString()->shouldReturn('exact("some\\nstring")'); | ||||
|     } | ||||
|  | ||||
|     function it_generates_proper_string_representation_for_double() | ||||
|     { | ||||
|         $this->beConstructedWith(42.3); | ||||
|         $this->__toString()->shouldReturn('exact(42.3)'); | ||||
|     } | ||||
|  | ||||
|     function it_generates_proper_string_representation_for_boolean_true() | ||||
|     { | ||||
|         $this->beConstructedWith(true); | ||||
|         $this->__toString()->shouldReturn('exact(true)'); | ||||
|     } | ||||
|  | ||||
|     function it_generates_proper_string_representation_for_boolean_false() | ||||
|     { | ||||
|         $this->beConstructedWith(false); | ||||
|         $this->__toString()->shouldReturn('exact(false)'); | ||||
|     } | ||||
|  | ||||
|     function it_generates_proper_string_representation_for_null() | ||||
|     { | ||||
|         $this->beConstructedWith(null); | ||||
|         $this->__toString()->shouldReturn('exact(null)'); | ||||
|     } | ||||
|  | ||||
|     function it_generates_proper_string_representation_for_empty_array() | ||||
|     { | ||||
|         $this->beConstructedWith(array()); | ||||
|         $this->__toString()->shouldReturn('exact([])'); | ||||
|     } | ||||
|  | ||||
|     function it_generates_proper_string_representation_for_array() | ||||
|     { | ||||
|         $this->beConstructedWith(array('zet', 42)); | ||||
|         $this->__toString()->shouldReturn('exact(["zet", 42])'); | ||||
|     } | ||||
|  | ||||
|     function it_generates_proper_string_representation_for_resource() | ||||
|     { | ||||
|         $resource = fopen(__FILE__, 'r'); | ||||
|         $this->beConstructedWith($resource); | ||||
|         $this->__toString()->shouldReturn('exact(stream:'.$resource.')'); | ||||
|     } | ||||
|  | ||||
|     /** | ||||
|      * @param \stdClass $object | ||||
|      */ | ||||
|     function it_generates_proper_string_representation_for_object($object) | ||||
|     { | ||||
|         $objHash = sprintf('%s:%s', | ||||
|             get_class($object->getWrappedObject()), | ||||
|             spl_object_hash($object->getWrappedObject()) | ||||
|         ); | ||||
|  | ||||
|         $this->beConstructedWith($object); | ||||
|         $this->__toString()->shouldReturn("exact($objHash Object (\n    'objectProphecy' => Prophecy\Prophecy\ObjectProphecy Object (*Prophecy*)\n))"); | ||||
|     } | ||||
| } | ||||
|  | ||||
| class ExactValueTokenFixtureA | ||||
| { | ||||
|     public $errors; | ||||
| } | ||||
|  | ||||
| class ExactValueTokenFixtureB extends ExactValueTokenFixtureA | ||||
| { | ||||
|     public $errors; | ||||
|     public $value = null; | ||||
|  | ||||
|     public function __construct($value) | ||||
|     { | ||||
|         $this->value = $value; | ||||
|     } | ||||
| } | ||||
| @@ -1,152 +0,0 @@ | ||||
| <?php | ||||
|  | ||||
| namespace spec\Prophecy\Argument\Token; | ||||
|  | ||||
| use PhpSpec\ObjectBehavior; | ||||
| use Prophecy\Argument; | ||||
|  | ||||
| class IdenticalValueTokenSpec extends ObjectBehavior | ||||
| { | ||||
|     function let() | ||||
|     { | ||||
|         $this->beConstructedWith(42); | ||||
|     } | ||||
|  | ||||
|     function it_is_initializable() | ||||
|     { | ||||
|         $this->shouldHaveType('Prophecy\Argument\Token\IdenticalValueToken'); | ||||
|     } | ||||
|  | ||||
|     function it_scores_11_if_string_value_is_identical_to_argument() | ||||
|     { | ||||
|         $this->beConstructedWith('foo'); | ||||
|         $this->scoreArgument('foo')->shouldReturn(11); | ||||
|     } | ||||
|  | ||||
|     function it_scores_11_if_boolean_value_is_identical_to_argument() | ||||
|     { | ||||
|         $this->beConstructedWith(false); | ||||
|         $this->scoreArgument(false)->shouldReturn(11); | ||||
|     } | ||||
|  | ||||
|     function it_scores_11_if_integer_value_is_identical_to_argument() | ||||
|     { | ||||
|         $this->beConstructedWith(31); | ||||
|         $this->scoreArgument(31)->shouldReturn(11); | ||||
|     } | ||||
|  | ||||
|     function it_scores_11_if_float_value_is_identical_to_argument() | ||||
|     { | ||||
|         $this->beConstructedWith(31.12); | ||||
|         $this->scoreArgument(31.12)->shouldReturn(11); | ||||
|     } | ||||
|  | ||||
|     function it_scores_11_if_array_value_is_identical_to_argument() | ||||
|     { | ||||
|         $this->beConstructedWith(array('foo' => 'bar')); | ||||
|         $this->scoreArgument(array('foo' => 'bar'))->shouldReturn(11); | ||||
|     } | ||||
|  | ||||
|     function it_scores_11_if_object_value_is_identical_to_argument() | ||||
|     { | ||||
|         $object = new \stdClass(); | ||||
|  | ||||
|         $this->beConstructedWith($object); | ||||
|         $this->scoreArgument($object)->shouldReturn(11); | ||||
|     } | ||||
|  | ||||
|     function it_scores_false_if_value_is_not_identical_to_argument() | ||||
|     { | ||||
|         $this->beConstructedWith(new \stdClass()); | ||||
|         $this->scoreArgument('foo')->shouldReturn(false); | ||||
|     } | ||||
|  | ||||
|     function it_scores_false_if_object_value_is_not_the_same_instance_than_argument() | ||||
|     { | ||||
|         $this->beConstructedWith(new \stdClass()); | ||||
|         $this->scoreArgument(new \stdClass())->shouldReturn(false); | ||||
|     } | ||||
|  | ||||
|     function it_scores_false_if_integer_value_is_not_identical_to_boolean_argument() | ||||
|     { | ||||
|         $this->beConstructedWith(1); | ||||
|         $this->scoreArgument(true)->shouldReturn(false); | ||||
|     } | ||||
|  | ||||
|     function it_is_not_last() | ||||
|     { | ||||
|         $this->shouldNotBeLast(); | ||||
|     } | ||||
|  | ||||
|     function it_generates_proper_string_representation_for_integer() | ||||
|     { | ||||
|         $this->beConstructedWith(42); | ||||
|         $this->__toString()->shouldReturn('identical(42)'); | ||||
|     } | ||||
|  | ||||
|     function it_generates_proper_string_representation_for_string() | ||||
|     { | ||||
|         $this->beConstructedWith('some string'); | ||||
|         $this->__toString()->shouldReturn('identical("some string")'); | ||||
|     } | ||||
|  | ||||
|     function it_generates_single_line_representation_for_multiline_string() | ||||
|     { | ||||
|         $this->beConstructedWith("some\nstring"); | ||||
|         $this->__toString()->shouldReturn('identical("some\\nstring")'); | ||||
|     } | ||||
|  | ||||
|     function it_generates_proper_string_representation_for_double() | ||||
|     { | ||||
|         $this->beConstructedWith(42.3); | ||||
|         $this->__toString()->shouldReturn('identical(42.3)'); | ||||
|     } | ||||
|  | ||||
|     function it_generates_proper_string_representation_for_boolean_true() | ||||
|     { | ||||
|         $this->beConstructedWith(true); | ||||
|         $this->__toString()->shouldReturn('identical(true)'); | ||||
|     } | ||||
|  | ||||
|     function it_generates_proper_string_representation_for_boolean_false() | ||||
|     { | ||||
|         $this->beConstructedWith(false); | ||||
|         $this->__toString()->shouldReturn('identical(false)'); | ||||
|     } | ||||
|  | ||||
|     function it_generates_proper_string_representation_for_null() | ||||
|     { | ||||
|         $this->beConstructedWith(null); | ||||
|         $this->__toString()->shouldReturn('identical(null)'); | ||||
|     } | ||||
|  | ||||
|     function it_generates_proper_string_representation_for_empty_array() | ||||
|     { | ||||
|         $this->beConstructedWith(array()); | ||||
|         $this->__toString()->shouldReturn('identical([])'); | ||||
|     } | ||||
|  | ||||
|     function it_generates_proper_string_representation_for_array() | ||||
|     { | ||||
|         $this->beConstructedWith(array('zet', 42)); | ||||
|         $this->__toString()->shouldReturn('identical(["zet", 42])'); | ||||
|     } | ||||
|  | ||||
|     function it_generates_proper_string_representation_for_resource() | ||||
|     { | ||||
|         $resource = fopen(__FILE__, 'r'); | ||||
|         $this->beConstructedWith($resource); | ||||
|         $this->__toString()->shouldReturn('identical(stream:'.$resource.')'); | ||||
|     } | ||||
|  | ||||
|     function it_generates_proper_string_representation_for_object($object) | ||||
|     { | ||||
|         $objHash = sprintf('%s:%s', | ||||
|             get_class($object->getWrappedObject()), | ||||
|             spl_object_hash($object->getWrappedObject()) | ||||
|         ); | ||||
|  | ||||
|         $this->beConstructedWith($object); | ||||
|         $this->__toString()->shouldReturn("identical($objHash Object (\n    'objectProphecy' => Prophecy\Prophecy\ObjectProphecy Object (*Prophecy*)\n))"); | ||||
|     } | ||||
| } | ||||
| @@ -1,78 +0,0 @@ | ||||
| <?php | ||||
|  | ||||
| namespace spec\Prophecy\Argument\Token; | ||||
|  | ||||
| use PhpSpec\ObjectBehavior; | ||||
| use Prophecy\Argument; | ||||
|  | ||||
| class LogicalAndTokenSpec extends ObjectBehavior | ||||
| { | ||||
|     function it_implements_TokenInterface() | ||||
|     { | ||||
|         $this->beConstructedWith(array()); | ||||
|         $this->shouldBeAnInstanceOf('Prophecy\Argument\Token\TokenInterface'); | ||||
|     } | ||||
|  | ||||
|     function it_is_not_last() | ||||
|     { | ||||
|         $this->beConstructedWith(array()); | ||||
|         $this->shouldNotBeLast(); | ||||
|     } | ||||
|  | ||||
|     /** | ||||
|      * @param \Prophecy\Argument\Token\TokenInterface $token1 | ||||
|      * @param \Prophecy\Argument\Token\TokenInterface $token2 | ||||
|      * @param \Prophecy\Argument\Token\TokenInterface $token3 | ||||
|      */ | ||||
|     function it_generates_string_representation_from_all_tokens_imploded($token1, $token2, $token3) | ||||
|     { | ||||
|         $token1->__toString()->willReturn('token_1'); | ||||
|         $token2->__toString()->willReturn('token_2'); | ||||
|         $token3->__toString()->willReturn('token_3'); | ||||
|  | ||||
|         $this->beConstructedWith(array($token1, $token2, $token3)); | ||||
|         $this->__toString()->shouldReturn('bool(token_1 AND token_2 AND token_3)'); | ||||
|     } | ||||
|  | ||||
|     function it_wraps_non_token_arguments_into_ExactValueToken() | ||||
|     { | ||||
|         $this->beConstructedWith(array(15, '1985')); | ||||
|         $this->__toString()->shouldReturn("bool(exact(15) AND exact(\"1985\"))"); | ||||
|     } | ||||
|  | ||||
|     /** | ||||
|      * @param \Prophecy\Argument\Token\TokenInterface $token1 | ||||
|      * @param \Prophecy\Argument\Token\TokenInterface $token2 | ||||
|      */ | ||||
|     function it_scores_the_maximum_score_from_all_scores_returned_by_tokens($token1, $token2) | ||||
|     { | ||||
|         $token1->scoreArgument(1)->willReturn(10); | ||||
|         $token2->scoreArgument(1)->willReturn(5); | ||||
|         $this->beConstructedWith(array($token1, $token2)); | ||||
|         $this->scoreArgument(1)->shouldReturn(10); | ||||
|     } | ||||
|  | ||||
|     function it_does_not_score_if_there_are_no_arguments_or_tokens() | ||||
|     { | ||||
|         $this->beConstructedWith(array()); | ||||
|         $this->scoreArgument('any')->shouldReturn(false); | ||||
|     } | ||||
|  | ||||
|     /** | ||||
|      * @param \Prophecy\Argument\Token\TokenInterface $token1 | ||||
|      * @param \Prophecy\Argument\Token\TokenInterface $token2 | ||||
|      */ | ||||
|     function it_does_not_score_if_either_of_tokens_does_not_score($token1, $token2) | ||||
|     { | ||||
|         $token1->scoreArgument(1)->willReturn(10); | ||||
|         $token1->scoreArgument(2)->willReturn(false); | ||||
|  | ||||
|         $token2->scoreArgument(1)->willReturn(false); | ||||
|         $token2->scoreArgument(2)->willReturn(10); | ||||
|  | ||||
|         $this->beConstructedWith(array($token1, $token2)); | ||||
|  | ||||
|         $this->scoreArgument(1)->shouldReturn(false); | ||||
|         $this->scoreArgument(2)->shouldReturn(false); | ||||
|     } | ||||
| } | ||||
| @@ -1,65 +0,0 @@ | ||||
| <?php | ||||
|  | ||||
| namespace spec\Prophecy\Argument\Token; | ||||
|  | ||||
| use PhpSpec\ObjectBehavior; | ||||
| use Prophecy\Argument\Token\TokenInterface; | ||||
|  | ||||
| class LogicalNotTokenSpec extends ObjectBehavior | ||||
| { | ||||
|     /** | ||||
|      * @param \Prophecy\Argument\Token\TokenInterface $token | ||||
|      */ | ||||
|     function let($token) | ||||
|     { | ||||
|         $this->beConstructedWith($token); | ||||
|     } | ||||
|  | ||||
|     function it_implements_TokenInterface() | ||||
|     { | ||||
|         $this->shouldBeAnInstanceOf('Prophecy\Argument\Token\TokenInterface'); | ||||
|     } | ||||
|  | ||||
|     function it_holds_originating_token($token) | ||||
|     { | ||||
|         $this->getOriginatingToken()->shouldReturn($token); | ||||
|     } | ||||
|  | ||||
|     function it_has_simple_string_representation($token) | ||||
|     { | ||||
|         $token->__toString()->willReturn('value'); | ||||
|         $this->__toString()->shouldBe('not(value)'); | ||||
|     } | ||||
|  | ||||
|     function it_wraps_non_token_argument_into_ExactValueToken() | ||||
|     { | ||||
|         $this->beConstructedWith(5); | ||||
|         $token = $this->getOriginatingToken(); | ||||
|         $token->shouldhaveType('Prophecy\Argument\Token\ExactValueToken'); | ||||
|         $token->getValue()->shouldBe(5); | ||||
|     } | ||||
|  | ||||
|     function it_scores_4_if_preset_token_does_not_match_the_argument($token) | ||||
|     { | ||||
|         $token->scoreArgument('argument')->willReturn(false); | ||||
|         $this->scoreArgument('argument')->shouldBe(4); | ||||
|     } | ||||
|  | ||||
|     function it_does_not_score_if_preset_token_matches_argument($token) | ||||
|     { | ||||
|         $token->scoreArgument('argument')->willReturn(5); | ||||
|         $this->scoreArgument('argument')->shouldBe(false); | ||||
|     } | ||||
|  | ||||
|     function it_is_last_if_preset_token_is_last($token) | ||||
|     { | ||||
|         $token->isLast()->willReturn(true); | ||||
|         $this->shouldBeLast(); | ||||
|     } | ||||
|  | ||||
|     function it_is_not_last_if_preset_token_is_not_last($token) | ||||
|     { | ||||
|         $token->isLast()->willReturn(false); | ||||
|         $this->shouldNotBeLast(); | ||||
|     } | ||||
| } | ||||
| @@ -1,101 +0,0 @@ | ||||
| <?php | ||||
|  | ||||
| namespace spec\Prophecy\Argument\Token; | ||||
|  | ||||
| use PhpSpec\ObjectBehavior; | ||||
|  | ||||
| class ObjectStateTokenSpec extends ObjectBehavior | ||||
| { | ||||
|     function let() | ||||
|     { | ||||
|         $this->beConstructedWith('getName', 'stdClass'); | ||||
|     } | ||||
|  | ||||
|     function it_implements_TokenInterface() | ||||
|     { | ||||
|         $this->shouldBeAnInstanceOf('Prophecy\Argument\Token\TokenInterface'); | ||||
|     } | ||||
|  | ||||
|     function it_is_not_last() | ||||
|     { | ||||
|         $this->shouldNotBeLast(); | ||||
|     } | ||||
|  | ||||
|     /** | ||||
|      * @param \ReflectionClass $reflection | ||||
|      */ | ||||
|     function it_scores_8_if_argument_object_has_specific_method_state($reflection) | ||||
|     { | ||||
|         $reflection->getName()->willReturn('stdClass'); | ||||
|  | ||||
|         $this->scoreArgument($reflection)->shouldReturn(8); | ||||
|     } | ||||
|  | ||||
|     /** | ||||
|      * @param \stdClass $class | ||||
|      */ | ||||
|     function it_scores_8_if_argument_object_has_specific_property_state($class) | ||||
|     { | ||||
|         $class->getName = 'stdClass'; | ||||
|  | ||||
|         $this->scoreArgument($class)->shouldReturn(8); | ||||
|     } | ||||
|  | ||||
|     function it_does_not_score_if_argument_method_state_does_not_match() | ||||
|     { | ||||
|         $value = new ObjectStateTokenFixtureB('ABC'); | ||||
|         $value2 = new ObjectStateTokenFixtureB('CBA'); | ||||
|  | ||||
|         $this->beConstructedWith('getSelf', $value); | ||||
|         $this->scoreArgument($value2)->shouldReturn(false); | ||||
|     } | ||||
|  | ||||
|     /** | ||||
|      * @param \stdClass $class | ||||
|      */ | ||||
|     function it_does_not_score_if_argument_property_state_does_not_match($class) | ||||
|     { | ||||
|         $class->getName = 'SplFileInfo'; | ||||
|  | ||||
|         $this->scoreArgument($class)->shouldReturn(false); | ||||
|     } | ||||
|  | ||||
|     /** | ||||
|      * @param \spec\Prophecy\Argument\Token\ObjectStateTokenFixtureA $class | ||||
|      */ | ||||
|     function it_does_not_score_if_argument_object_does_not_have_method_or_property($class) | ||||
|     { | ||||
|         $this->scoreArgument($class)->shouldReturn(false); | ||||
|     } | ||||
|  | ||||
|     function it_does_not_score_if_argument_is_not_object() | ||||
|     { | ||||
|         $this->scoreArgument(42)->shouldReturn(false); | ||||
|     } | ||||
|  | ||||
|     function it_has_simple_string_representation() | ||||
|     { | ||||
|         $this->__toString()->shouldReturn('state(getName(), "stdClass")'); | ||||
|     } | ||||
| } | ||||
|  | ||||
| class ObjectStateTokenFixtureA | ||||
| { | ||||
|     public $errors; | ||||
| } | ||||
|  | ||||
| class ObjectStateTokenFixtureB extends ObjectStateTokenFixtureA | ||||
| { | ||||
|     public $errors; | ||||
|     public $value = null; | ||||
|  | ||||
|     public function __construct($value) | ||||
|     { | ||||
|         $this->value = $value; | ||||
|     } | ||||
|  | ||||
|     public function getSelf() | ||||
|     { | ||||
|         return $this; | ||||
|     } | ||||
| } | ||||
| @@ -1,49 +0,0 @@ | ||||
| <?php | ||||
|  | ||||
| namespace spec\Prophecy\Argument\Token; | ||||
|  | ||||
| use PhpSpec\ObjectBehavior; | ||||
| use Prophecy\Argument; | ||||
|  | ||||
| class StringContainsTokenSpec extends ObjectBehavior | ||||
| { | ||||
|     function let() | ||||
|     { | ||||
|         $this->beConstructedWith('a substring'); | ||||
|     } | ||||
|  | ||||
|     function it_is_initializable() | ||||
|     { | ||||
|         $this->shouldHaveType('Prophecy\Argument\Token\StringContainsToken'); | ||||
|     } | ||||
|  | ||||
|     function it_implements_TokenInterface() | ||||
|     { | ||||
|         $this->shouldBeAnInstanceOf('Prophecy\Argument\Token\TokenInterface'); | ||||
|     } | ||||
|  | ||||
|     function it_holds_value() | ||||
|     { | ||||
|         $this->getValue()->shouldReturn('a substring'); | ||||
|     } | ||||
|  | ||||
|     function it_is_not_last() | ||||
|     { | ||||
|         $this->shouldNotBeLast(); | ||||
|     } | ||||
|  | ||||
|     function it_scores_6_if_the_argument_contains_the_value() | ||||
|     { | ||||
|         $this->scoreArgument('Argument containing a substring')->shouldReturn(6); | ||||
|     } | ||||
|  | ||||
|     function it_does_not_score_if_the_argument_does_not_contain_the_value() | ||||
|     { | ||||
|         $this->scoreArgument('Argument will not match')->shouldReturn(false); | ||||
|     } | ||||
|  | ||||
|     function its_string_representation_shows_substring() | ||||
|     { | ||||
|         $this->__toString()->shouldReturn('contains("a substring")'); | ||||
|     } | ||||
| } | ||||
| @@ -1,59 +0,0 @@ | ||||
| <?php | ||||
|  | ||||
| namespace spec\Prophecy\Argument\Token; | ||||
|  | ||||
| use PhpSpec\ObjectBehavior; | ||||
|  | ||||
| class TypeTokenSpec extends ObjectBehavior | ||||
| { | ||||
|     function let() | ||||
|     { | ||||
|         $this->beConstructedWith('integer'); | ||||
|     } | ||||
|  | ||||
|     function it_implements_TokenInterface() | ||||
|     { | ||||
|         $this->shouldBeAnInstanceOf('Prophecy\Argument\Token\TokenInterface'); | ||||
|     } | ||||
|  | ||||
|     function it_is_not_last() | ||||
|     { | ||||
|         $this->shouldNotBeLast(); | ||||
|     } | ||||
|  | ||||
|     function it_scores_5_if_argument_matches_simple_type() | ||||
|     { | ||||
|         $this->beConstructedWith('integer'); | ||||
|  | ||||
|         $this->scoreArgument(42)->shouldReturn(5); | ||||
|     } | ||||
|  | ||||
|     function it_does_not_scores_if_argument_does_not_match_simple_type() | ||||
|     { | ||||
|         $this->beConstructedWith('integer'); | ||||
|  | ||||
|         $this->scoreArgument(42.0)->shouldReturn(false); | ||||
|     } | ||||
|  | ||||
|     /** | ||||
|      * @param \ReflectionObject $object | ||||
|      */ | ||||
|     function it_scores_5_if_argument_is_an_instance_of_specified_class($object) | ||||
|     { | ||||
|         $this->beConstructedWith('ReflectionClass'); | ||||
|  | ||||
|         $this->scoreArgument($object)->shouldReturn(5); | ||||
|     } | ||||
|  | ||||
|     function it_has_simple_string_representation() | ||||
|     { | ||||
|         $this->__toString()->shouldReturn('type(integer)'); | ||||
|     } | ||||
|  | ||||
|     function it_scores_5_if_argument_is_an_instance_of_specified_interface(\Prophecy\Argument\Token\TokenInterface $interface) | ||||
|     { | ||||
|         $this->beConstructedWith('Prophecy\Argument\Token\TokenInterface'); | ||||
|  | ||||
|         $this->scoreArgument($interface)->shouldReturn(5); | ||||
|     } | ||||
| } | ||||
| @@ -1,101 +0,0 @@ | ||||
| <?php | ||||
|  | ||||
| namespace spec\Prophecy; | ||||
|  | ||||
| use PhpSpec\ObjectBehavior; | ||||
|  | ||||
| class ArgumentSpec extends ObjectBehavior | ||||
| { | ||||
|     function it_has_a_shortcut_for_exact_argument_token() | ||||
|     { | ||||
|         $token = $this->exact(42); | ||||
|         $token->shouldBeAnInstanceOf('Prophecy\Argument\Token\ExactValueToken'); | ||||
|         $token->getValue()->shouldReturn(42); | ||||
|     } | ||||
|  | ||||
|     function it_has_a_shortcut_for_any_argument_token() | ||||
|     { | ||||
|         $token = $this->any(); | ||||
|         $token->shouldBeAnInstanceOf('Prophecy\Argument\Token\AnyValueToken'); | ||||
|     } | ||||
|  | ||||
|     function it_has_a_shortcut_for_multiple_arguments_token() | ||||
|     { | ||||
|         $token = $this->cetera(); | ||||
|         $token->shouldBeAnInstanceOf('Prophecy\Argument\Token\AnyValuesToken'); | ||||
|     } | ||||
|  | ||||
|     function it_has_a_shortcut_for_type_token() | ||||
|     { | ||||
|         $token = $this->type('integer'); | ||||
|         $token->shouldBeAnInstanceOf('Prophecy\Argument\Token\TypeToken'); | ||||
|     } | ||||
|  | ||||
|     function it_has_a_shortcut_for_callback_token() | ||||
|     { | ||||
|         $token = $this->that('get_class'); | ||||
|         $token->shouldBeAnInstanceOf('Prophecy\Argument\Token\CallbackToken'); | ||||
|     } | ||||
|  | ||||
|     function it_has_a_shortcut_for_object_state_token() | ||||
|     { | ||||
|         $token = $this->which('getName', 'everzet'); | ||||
|         $token->shouldBeAnInstanceOf('Prophecy\Argument\Token\ObjectStateToken'); | ||||
|     } | ||||
|  | ||||
|     function it_has_a_shortcut_for_logical_and_token() | ||||
|     { | ||||
|         $token = $this->allOf('integer', 5); | ||||
|         $token->shouldBeAnInstanceOf('Prophecy\Argument\Token\LogicalAndToken'); | ||||
|     } | ||||
|  | ||||
|     function it_has_a_shortcut_for_array_count_token() | ||||
|     { | ||||
|         $token = $this->size(5); | ||||
|         $token->shouldBeAnInstanceOf('Prophecy\Argument\Token\ArrayCountToken'); | ||||
|     } | ||||
|  | ||||
|     function it_has_a_shortcut_for_array_entry_token() | ||||
|     { | ||||
|         $token = $this->withEntry('key', 'value'); | ||||
|         $token->shouldBeAnInstanceOf('Prophecy\Argument\Token\ArrayEntryToken'); | ||||
|     } | ||||
|  | ||||
|     function it_has_a_shortcut_for_array_every_entry_token() | ||||
|     { | ||||
|         $token = $this->withEveryEntry('value'); | ||||
|         $token->shouldBeAnInstanceOf('Prophecy\Argument\Token\ArrayEveryEntryToken'); | ||||
|     } | ||||
|  | ||||
|     function it_has_a_shortcut_for_identical_value_token() | ||||
|     { | ||||
|         $token = $this->is('value'); | ||||
|         $token->shouldBeAnInstanceOf('Prophecy\Argument\Token\IdenticalValueToken'); | ||||
|     } | ||||
|  | ||||
|     function it_has_a_shortcut_for_array_entry_token_matching_any_key() | ||||
|     { | ||||
|         $token = $this->containing('value'); | ||||
|         $token->shouldBeAnInstanceOf('Prophecy\Argument\Token\ArrayEntryToken'); | ||||
|         $token->getKey()->shouldHaveType('Prophecy\Argument\Token\AnyValueToken'); | ||||
|     } | ||||
|  | ||||
|     function it_has_a_shortcut_for_array_entry_token_matching_any_value() | ||||
|     { | ||||
|         $token = $this->withKey('key'); | ||||
|         $token->shouldBeAnInstanceOf('Prophecy\Argument\Token\ArrayEntryToken'); | ||||
|         $token->getValue()->shouldHaveType('Prophecy\Argument\Token\AnyValueToken'); | ||||
|     } | ||||
|  | ||||
|     function it_has_a_shortcut_for_logical_not_token() | ||||
|     { | ||||
|         $token = $this->not('kagux'); | ||||
|         $token->shouldBeAnInstanceOf('Prophecy\Argument\Token\LogicalNotToken'); | ||||
|     } | ||||
|  | ||||
|     function it_has_a_shortcut_for_string_contains_token() | ||||
|     { | ||||
|         $token = $this->containingString('string'); | ||||
|         $token->shouldBeAnInstanceOf('Prophecy\Argument\Token\StringContainsToken'); | ||||
|     } | ||||
| } | ||||
| @@ -1,188 +0,0 @@ | ||||
| <?php | ||||
|  | ||||
| namespace spec\Prophecy\Call; | ||||
|  | ||||
| use PhpSpec\ObjectBehavior; | ||||
| use Prophecy\Prophecy\ObjectProphecy; | ||||
| use Prophecy\Argument\ArgumentsWildcard; | ||||
|  | ||||
| class CallCenterSpec extends ObjectBehavior | ||||
| { | ||||
|     function let(ObjectProphecy $objectProphecy) | ||||
|     { | ||||
|     } | ||||
|  | ||||
|     function it_records_calls_made_through_makeCall_method(ObjectProphecy $objectProphecy, ArgumentsWildcard $wildcard) | ||||
|     { | ||||
|         $wildcard->scoreArguments(array(5, 2, 3))->willReturn(10); | ||||
|         $objectProphecy->getMethodProphecies()->willReturn(array()); | ||||
|  | ||||
|         $this->makeCall($objectProphecy, 'setValues', array(5, 2, 3)); | ||||
|  | ||||
|         $calls = $this->findCalls('setValues', $wildcard); | ||||
|         $calls->shouldHaveCount(1); | ||||
|  | ||||
|         $calls[0]->shouldBeAnInstanceOf('Prophecy\Call\Call'); | ||||
|         $calls[0]->getMethodName()->shouldReturn('setValues'); | ||||
|         $calls[0]->getArguments()->shouldReturn(array(5, 2, 3)); | ||||
|         $calls[0]->getReturnValue()->shouldReturn(null); | ||||
|     } | ||||
|  | ||||
|     function it_returns_null_for_any_call_through_makeCall_if_no_method_prophecies_added( | ||||
|         $objectProphecy | ||||
|     ) | ||||
|     { | ||||
|         $objectProphecy->getMethodProphecies()->willReturn(array()); | ||||
|  | ||||
|         $this->makeCall($objectProphecy, 'setValues', array(5, 2, 3))->shouldReturn(null); | ||||
|     } | ||||
|  | ||||
|     /** | ||||
|      * @param \Prophecy\Prophecy\MethodProphecy    $method1 | ||||
|      * @param \Prophecy\Prophecy\MethodProphecy    $method2 | ||||
|      * @param \Prophecy\Prophecy\MethodProphecy    $method3 | ||||
|      * @param \Prophecy\Argument\ArgumentsWildcard $arguments1 | ||||
|      * @param \Prophecy\Argument\ArgumentsWildcard $arguments2 | ||||
|      * @param \Prophecy\Argument\ArgumentsWildcard $arguments3 | ||||
|      * @param \Prophecy\Promise\PromiseInterface   $promise | ||||
|      */ | ||||
|     function it_executes_promise_of_method_prophecy_that_matches_signature_passed_to_makeCall( | ||||
|         $objectProphecy, $method1, $method2, $method3, $arguments1, $arguments2, $arguments3, | ||||
|         $promise | ||||
|     ) | ||||
|     { | ||||
|         $method1->getMethodName()->willReturn('getName'); | ||||
|         $method1->getArgumentsWildcard()->willReturn($arguments1); | ||||
|         $arguments1->scoreArguments(array('world', 'everything'))->willReturn(false); | ||||
|  | ||||
|         $method2->getMethodName()->willReturn('setTitle'); | ||||
|         $method2->getArgumentsWildcard()->willReturn($arguments2); | ||||
|         $arguments2->scoreArguments(array('world', 'everything'))->willReturn(false); | ||||
|  | ||||
|         $method3->getMethodName()->willReturn('getName'); | ||||
|         $method3->getArgumentsWildcard()->willReturn($arguments3); | ||||
|         $method3->getPromise()->willReturn($promise); | ||||
|         $arguments3->scoreArguments(array('world', 'everything'))->willReturn(200); | ||||
|  | ||||
|         $objectProphecy->getMethodProphecies()->willReturn(array( | ||||
|             'method1' => array($method1), | ||||
|             'method2' => array($method2, $method3) | ||||
|         )); | ||||
|         $objectProphecy->getMethodProphecies('getName')->willReturn(array($method1, $method3)); | ||||
|         $objectProphecy->reveal()->willReturn(new \stdClass()); | ||||
|  | ||||
|         $promise->execute(array('world', 'everything'), $objectProphecy->getWrappedObject(), $method3)->willReturn(42); | ||||
|  | ||||
|         $this->makeCall($objectProphecy, 'getName', array('world', 'everything'))->shouldReturn(42); | ||||
|  | ||||
|         $calls = $this->findCalls('getName', $arguments3); | ||||
|         $calls->shouldHaveCount(1); | ||||
|         $calls[0]->getReturnValue()->shouldReturn(42); | ||||
|     } | ||||
|  | ||||
|     /** | ||||
|      * @param \Prophecy\Prophecy\MethodProphecy    $method1 | ||||
|      * @param \Prophecy\Prophecy\MethodProphecy    $method2 | ||||
|      * @param \Prophecy\Prophecy\MethodProphecy    $method3 | ||||
|      * @param \Prophecy\Argument\ArgumentsWildcard $arguments1 | ||||
|      * @param \Prophecy\Argument\ArgumentsWildcard $arguments2 | ||||
|      * @param \Prophecy\Argument\ArgumentsWildcard $arguments3 | ||||
|      * @param \Prophecy\Promise\PromiseInterface   $promise | ||||
|      */ | ||||
|     function it_executes_promise_of_method_prophecy_that_matches_with_highest_score_to_makeCall( | ||||
|         $objectProphecy, $method1, $method2, $method3, $arguments1, $arguments2, $arguments3, | ||||
|         $promise | ||||
|     ) | ||||
|     { | ||||
|         $method1->getMethodName()->willReturn('getName'); | ||||
|         $method1->getArgumentsWildcard()->willReturn($arguments1); | ||||
|         $arguments1->scoreArguments(array('world', 'everything'))->willReturn(50); | ||||
|  | ||||
|         $method2->getMethodName()->willReturn('getName'); | ||||
|         $method2->getArgumentsWildcard()->willReturn($arguments2); | ||||
|         $method2->getPromise()->willReturn($promise); | ||||
|         $arguments2->scoreArguments(array('world', 'everything'))->willReturn(300); | ||||
|  | ||||
|         $method3->getMethodName()->willReturn('getName'); | ||||
|         $method3->getArgumentsWildcard()->willReturn($arguments3); | ||||
|         $arguments3->scoreArguments(array('world', 'everything'))->willReturn(200); | ||||
|  | ||||
|         $objectProphecy->getMethodProphecies()->willReturn(array( | ||||
|             'method1' => array($method1), | ||||
|             'method2' => array($method2, $method3) | ||||
|         )); | ||||
|         $objectProphecy->getMethodProphecies('getName')->willReturn(array( | ||||
|             $method1, $method2, $method3 | ||||
|         )); | ||||
|         $objectProphecy->reveal()->willReturn(new \stdClass()); | ||||
|  | ||||
|         $promise->execute(array('world', 'everything'), $objectProphecy->getWrappedObject(), $method2) | ||||
|             ->willReturn('second'); | ||||
|  | ||||
|         $this->makeCall($objectProphecy, 'getName', array('world', 'everything')) | ||||
|             ->shouldReturn('second'); | ||||
|     } | ||||
|  | ||||
|     /** | ||||
|      * @param \Prophecy\Prophecy\MethodProphecy    $method | ||||
|      * @param \Prophecy\Argument\ArgumentsWildcard $arguments | ||||
|      */ | ||||
|     function it_throws_exception_if_call_does_not_match_any_of_defined_method_prophecies( | ||||
|         $objectProphecy, $method, $arguments | ||||
|     ) | ||||
|     { | ||||
|         $method->getMethodName()->willReturn('getName'); | ||||
|         $method->getArgumentsWildcard()->willReturn($arguments); | ||||
|         $arguments->scoreArguments(array('world', 'everything'))->willReturn(false); | ||||
|         $arguments->__toString()->willReturn('arg1, arg2'); | ||||
|  | ||||
|         $objectProphecy->getMethodProphecies()->willReturn(array('method1' => array($method))); | ||||
|         $objectProphecy->getMethodProphecies('getName')->willReturn(array($method)); | ||||
|  | ||||
|         $this->shouldThrow('Prophecy\Exception\Call\UnexpectedCallException') | ||||
|             ->duringMakeCall($objectProphecy, 'getName', array('world', 'everything')); | ||||
|     } | ||||
|  | ||||
|     /** | ||||
|      * @param \Prophecy\Prophecy\MethodProphecy    $method | ||||
|      * @param \Prophecy\Argument\ArgumentsWildcard $arguments | ||||
|      */ | ||||
|     function it_returns_null_if_method_prophecy_that_matches_makeCall_arguments_has_no_promise( | ||||
|         $objectProphecy, $method, $arguments | ||||
|     ) | ||||
|     { | ||||
|         $method->getMethodName()->willReturn('getName'); | ||||
|         $method->getArgumentsWildcard()->willReturn($arguments); | ||||
|         $method->getPromise()->willReturn(null); | ||||
|         $arguments->scoreArguments(array('world', 'everything'))->willReturn(100); | ||||
|  | ||||
|         $objectProphecy->getMethodProphecies()->willReturn(array($method)); | ||||
|         $objectProphecy->getMethodProphecies('getName')->willReturn(array($method)); | ||||
|  | ||||
|         $this->makeCall($objectProphecy, 'getName', array('world', 'everything')) | ||||
|             ->shouldReturn(null); | ||||
|     } | ||||
|  | ||||
|     /** | ||||
|      * @param \Prophecy\Argument\ArgumentsWildcard $wildcard | ||||
|      */ | ||||
|     function it_finds_recorded_calls_by_a_method_name_and_arguments_wildcard( | ||||
|         $objectProphecy, $wildcard | ||||
|     ) | ||||
|     { | ||||
|         $objectProphecy->getMethodProphecies()->willReturn(array()); | ||||
|  | ||||
|         $this->makeCall($objectProphecy, 'getName', array('world')); | ||||
|         $this->makeCall($objectProphecy, 'getName', array('everything')); | ||||
|         $this->makeCall($objectProphecy, 'setName', array(42)); | ||||
|  | ||||
|         $wildcard->scoreArguments(array('world'))->willReturn(false); | ||||
|         $wildcard->scoreArguments(array('everything'))->willReturn(10); | ||||
|  | ||||
|         $calls = $this->findCalls('getName', $wildcard); | ||||
|  | ||||
|         $calls->shouldHaveCount(1); | ||||
|         $calls[0]->getMethodName()->shouldReturn('getName'); | ||||
|         $calls[0]->getArguments()->shouldReturn(array('everything')); | ||||
|     } | ||||
| } | ||||
| @@ -1,54 +0,0 @@ | ||||
| <?php | ||||
|  | ||||
| namespace spec\Prophecy\Call; | ||||
|  | ||||
| use PhpSpec\ObjectBehavior; | ||||
|  | ||||
| class CallSpec extends ObjectBehavior | ||||
| { | ||||
|     /** | ||||
|      * @param \Exception $exception | ||||
|      */ | ||||
|     function let($exception) | ||||
|     { | ||||
|         $this->beConstructedWith('setValues', array(5, 2), 42, $exception, 'some_file.php', 23); | ||||
|     } | ||||
|  | ||||
|     function it_exposes_method_name_through_getter() | ||||
|     { | ||||
|         $this->getMethodName()->shouldReturn('setValues'); | ||||
|     } | ||||
|  | ||||
|     function it_exposes_arguments_through_getter() | ||||
|     { | ||||
|         $this->getArguments()->shouldReturn(array(5, 2)); | ||||
|     } | ||||
|  | ||||
|     function it_exposes_return_value_through_getter() | ||||
|     { | ||||
|         $this->getReturnValue()->shouldReturn(42); | ||||
|     } | ||||
|  | ||||
|     function it_exposes_exception_through_getter($exception) | ||||
|     { | ||||
|         $this->getException()->shouldReturn($exception); | ||||
|     } | ||||
|  | ||||
|     function it_exposes_file_and_line_through_getter() | ||||
|     { | ||||
|         $this->getFile()->shouldReturn('some_file.php'); | ||||
|         $this->getLine()->shouldReturn(23); | ||||
|     } | ||||
|  | ||||
|     function it_returns_shortpath_to_callPlace() | ||||
|     { | ||||
|         $this->getCallPlace()->shouldReturn('some_file.php:23'); | ||||
|     } | ||||
|  | ||||
|     function it_returns_unknown_as_callPlace_if_no_file_or_line_provided() | ||||
|     { | ||||
|         $this->beConstructedWith('setValues', array(), 0, null, null, null); | ||||
|  | ||||
|         $this->getCallPlace()->shouldReturn('unknown'); | ||||
|     } | ||||
| } | ||||
| @@ -1,39 +0,0 @@ | ||||
| <?php | ||||
|  | ||||
| namespace spec\Prophecy\Comparator; | ||||
|  | ||||
| use PhpSpec\ObjectBehavior; | ||||
| use Prophecy\Argument; | ||||
|  | ||||
| class ClosureComparatorSpec extends ObjectBehavior | ||||
| { | ||||
|     function it_is_comparator() | ||||
|     { | ||||
|         $this->shouldHaveType('SebastianBergmann\Comparator\Comparator'); | ||||
|     } | ||||
|  | ||||
|     function it_accepts_only_closures() | ||||
|     { | ||||
|         $this->accepts(123, 321)->shouldReturn(false); | ||||
|         $this->accepts('string', 'string')->shouldReturn(false); | ||||
|         $this->accepts(false, true)->shouldReturn(false); | ||||
|         $this->accepts(true, false)->shouldReturn(false); | ||||
|         $this->accepts((object)array(), (object)array())->shouldReturn(false); | ||||
|         $this->accepts(function(){}, (object)array())->shouldReturn(false); | ||||
|         $this->accepts(function(){}, (object)array())->shouldReturn(false); | ||||
|  | ||||
|         $this->accepts(function(){}, function(){})->shouldReturn(true); | ||||
|     } | ||||
|  | ||||
|     function it_asserts_that_all_closures_are_different() | ||||
|     { | ||||
|         $this->shouldThrow()->duringAssertEquals(function(){}, function(){}); | ||||
|     } | ||||
|  | ||||
|     function it_asserts_that_all_closures_are_different_even_if_its_the_same_closure() | ||||
|     { | ||||
|         $closure = function(){}; | ||||
|  | ||||
|         $this->shouldThrow()->duringAssertEquals($closure, $closure); | ||||
|     } | ||||
| } | ||||
| @@ -1,20 +0,0 @@ | ||||
| <?php | ||||
|  | ||||
| namespace spec\Prophecy\Comparator; | ||||
|  | ||||
| use PhpSpec\ObjectBehavior; | ||||
| use Prophecy\Argument; | ||||
|  | ||||
| class FactorySpec extends ObjectBehavior | ||||
| { | ||||
|     function it_extends_Sebastian_Comparator_Factory() | ||||
|     { | ||||
|         $this->shouldHaveType('SebastianBergmann\Comparator\Factory'); | ||||
|     } | ||||
|  | ||||
|     function it_should_have_ClosureComparator_registered() | ||||
|     { | ||||
|         $comparator = $this->getInstance()->getComparatorFor(function(){}, function(){}); | ||||
|         $comparator->shouldHaveType('Prophecy\Comparator\ClosureComparator'); | ||||
|     } | ||||
| } | ||||
| @@ -1,59 +0,0 @@ | ||||
| <?php | ||||
|  | ||||
| namespace spec\Prophecy\Doubler\ClassPatch; | ||||
|  | ||||
| use PhpSpec\ObjectBehavior; | ||||
| use Prophecy\Argument; | ||||
|  | ||||
| class DisableConstructorPatchSpec extends ObjectBehavior | ||||
| { | ||||
|     function it_is_a_patch() | ||||
|     { | ||||
|         $this->shouldBeAnInstanceOf('Prophecy\Doubler\ClassPatch\ClassPatchInterface'); | ||||
|     } | ||||
|  | ||||
|     function its_priority_is_100() | ||||
|     { | ||||
|         $this->getPriority()->shouldReturn(100); | ||||
|     } | ||||
|  | ||||
|     /** | ||||
|      * @param \Prophecy\Doubler\Generator\Node\ClassNode $node | ||||
|      */ | ||||
|     function it_supports_anything($node) | ||||
|     { | ||||
|         $this->supports($node)->shouldReturn(true); | ||||
|     } | ||||
|  | ||||
|     /** | ||||
|      * @param \Prophecy\Doubler\Generator\Node\ClassNode    $class | ||||
|      * @param \Prophecy\Doubler\Generator\Node\MethodNode   $method | ||||
|      * @param \Prophecy\Doubler\Generator\Node\ArgumentNode $arg1 | ||||
|      * @param \Prophecy\Doubler\Generator\Node\ArgumentNode $arg2 | ||||
|      */ | ||||
|     function it_makes_all_constructor_arguments_optional($class, $method, $arg1, $arg2) | ||||
|     { | ||||
|         $class->hasMethod('__construct')->willReturn(true); | ||||
|         $class->getMethod('__construct')->willReturn($method); | ||||
|         $method->getArguments()->willReturn(array($arg1, $arg2)); | ||||
|  | ||||
|         $arg1->setDefault(null)->shouldBeCalled(); | ||||
|         $arg2->setDefault(null)->shouldBeCalled(); | ||||
|  | ||||
|         $method->setCode(Argument::type('string'))->shouldBeCalled(); | ||||
|  | ||||
|         $this->apply($class); | ||||
|     } | ||||
|  | ||||
|     /** | ||||
|      * @param \Prophecy\Doubler\Generator\Node\ClassNode $class | ||||
|      */ | ||||
|     function it_creates_new_constructor_if_object_has_none($class) | ||||
|     { | ||||
|         $class->hasMethod('__construct')->willReturn(false); | ||||
|         $class->addMethod(Argument::type('Prophecy\Doubler\Generator\Node\MethodNode')) | ||||
|             ->shouldBeCalled(); | ||||
|  | ||||
|         $this->apply($class); | ||||
|     } | ||||
| } | ||||
| @@ -1,37 +0,0 @@ | ||||
| <?php | ||||
|  | ||||
| namespace spec\Prophecy\Doubler\ClassPatch; | ||||
|  | ||||
| use PhpSpec\ObjectBehavior; | ||||
| use Prophecy\Argument; | ||||
|  | ||||
| class HhvmExceptionPatchSpec extends ObjectBehavior | ||||
| { | ||||
|     function it_is_a_patch() | ||||
|     { | ||||
|         $this->shouldBeAnInstanceOf('Prophecy\Doubler\ClassPatch\ClassPatchInterface'); | ||||
|     } | ||||
|  | ||||
|     function its_priority_is_minus_50() | ||||
|     { | ||||
|         $this->getPriority()->shouldReturn(-50); | ||||
|     } | ||||
|  | ||||
|     /** | ||||
|      * @param \Prophecy\Doubler\Generator\Node\ClassNode  $node | ||||
|      * @param \Prophecy\Doubler\Generator\Node\MethodNode $method | ||||
|      * @param \Prophecy\Doubler\Generator\Node\MethodNode $getterMethod | ||||
|      */ | ||||
|     function it_uses_parent_code_for_setTraceOptions($node, $method, $getterMethod) | ||||
|     { | ||||
|         $node->hasMethod('setTraceOptions')->willReturn(true); | ||||
|         $node->getMethod('setTraceOptions')->willReturn($method); | ||||
|         $node->hasMethod('getTraceOptions')->willReturn(true); | ||||
|         $node->getMethod('getTraceOptions')->willReturn($getterMethod); | ||||
|  | ||||
|         $method->useParentCode()->shouldBeCalled(); | ||||
|         $getterMethod->useParentCode()->shouldBeCalled(); | ||||
|  | ||||
|         $this->apply($node); | ||||
|     } | ||||
| } | ||||
| @@ -1,44 +0,0 @@ | ||||
| <?php | ||||
|  | ||||
| namespace spec\Prophecy\Doubler\ClassPatch; | ||||
|  | ||||
| use PhpSpec\ObjectBehavior; | ||||
| use Prophecy\Argument; | ||||
| use Prophecy\Doubler\Generator\Node\MethodNode; | ||||
|  | ||||
| class KeywordPatchSpec extends ObjectBehavior | ||||
| { | ||||
|     function it_is_a_patch() | ||||
|     { | ||||
|         $this->shouldBeAnInstanceOf('Prophecy\Doubler\ClassPatch\ClassPatchInterface'); | ||||
|     } | ||||
|  | ||||
|     function its_priority_is_49() | ||||
|     { | ||||
|         $this->getPriority()->shouldReturn(49); | ||||
|     } | ||||
|  | ||||
|     /** | ||||
|      * @param \Prophecy\Doubler\Generator\Node\ClassNode $node | ||||
|      * @param \Prophecy\Doubler\Generator\Node\MethodNode $method1 | ||||
|      * @param \Prophecy\Doubler\Generator\Node\MethodNode $method2 | ||||
|      * @param \Prophecy\Doubler\Generator\Node\MethodNode $method3 | ||||
|      */ | ||||
|     function it_will_remove_echo_and_eval_methods($node, $method1, $method2, $method3) | ||||
|     { | ||||
|         $node->removeMethod('eval')->shouldBeCalled(); | ||||
|         $node->removeMethod('echo')->shouldBeCalled(); | ||||
|  | ||||
|         $method1->getName()->willReturn('echo'); | ||||
|         $method2->getName()->willReturn('eval'); | ||||
|         $method3->getName()->willReturn('notKeyword'); | ||||
|  | ||||
|         $node->getMethods()->willReturn(array( | ||||
|             'echo' => $method1, | ||||
|             'eval' => $method2, | ||||
|             'notKeyword' => $method3, | ||||
|         )); | ||||
|  | ||||
|         $this->apply($node); | ||||
|     } | ||||
| } | ||||
| @@ -1,76 +0,0 @@ | ||||
| <?php | ||||
|  | ||||
| namespace spec\Prophecy\Doubler\ClassPatch; | ||||
|  | ||||
| use PhpSpec\ObjectBehavior; | ||||
| use Prophecy\Argument; | ||||
| use Prophecy\Doubler\Generator\Node\MethodNode; | ||||
|  | ||||
| class MagicCallPatchSpec extends ObjectBehavior | ||||
| { | ||||
|     function it_is_a_patch() | ||||
|     { | ||||
|         $this->shouldBeAnInstanceOf('Prophecy\Doubler\ClassPatch\ClassPatchInterface'); | ||||
|     } | ||||
|  | ||||
|     /** | ||||
|      * @param \Prophecy\Doubler\Generator\Node\ClassNode $node | ||||
|      */ | ||||
|     function it_supports_anything($node) | ||||
|     { | ||||
|         $this->supports($node)->shouldReturn(true); | ||||
|     } | ||||
|  | ||||
|     /** | ||||
|      * @param \Prophecy\Doubler\Generator\Node\ClassNode $node | ||||
|      */ | ||||
|     function it_discovers_api_using_phpdoc($node) | ||||
|     { | ||||
|         $node->getParentClass()->willReturn('spec\Prophecy\Doubler\ClassPatch\MagicalApi'); | ||||
|  | ||||
|         $node->addMethod(new MethodNode('undefinedMethod'))->shouldBeCalled(); | ||||
|  | ||||
|         $this->apply($node); | ||||
|     } | ||||
|  | ||||
|     /** | ||||
|      * @param \Prophecy\Doubler\Generator\Node\ClassNode $node | ||||
|      */ | ||||
|     function it_ignores_existing_methods($node) | ||||
|     { | ||||
|         $node->getParentClass()->willReturn('spec\Prophecy\Doubler\ClassPatch\MagicalApiExtended'); | ||||
|  | ||||
|         $node->addMethod(new MethodNode('undefinedMethod'))->shouldBeCalled(); | ||||
|         $node->addMethod(new MethodNode('definedMethod'))->shouldNotBeCalled(); | ||||
|  | ||||
|         $this->apply($node); | ||||
|     } | ||||
|  | ||||
|     function it_has_50_priority() | ||||
|     { | ||||
|         $this->getPriority()->shouldReturn(50); | ||||
|     } | ||||
| } | ||||
|  | ||||
| /** | ||||
|  * @method void undefinedMethod() | ||||
|  */ | ||||
| class MagicalApi | ||||
| { | ||||
|     /** | ||||
|      * @return void | ||||
|      */ | ||||
|     public function definedMethod() | ||||
|     { | ||||
|  | ||||
|     } | ||||
| } | ||||
|  | ||||
| /** | ||||
|  * @method void undefinedMethod() | ||||
|  * @method void definedMethod() | ||||
|  */ | ||||
| class MagicalApiExtended extends MagicalApi | ||||
| { | ||||
|  | ||||
| } | ||||
| @@ -1,83 +0,0 @@ | ||||
| <?php | ||||
|  | ||||
| namespace spec\Prophecy\Doubler\ClassPatch; | ||||
|  | ||||
| use PhpSpec\ObjectBehavior; | ||||
| use Prophecy\Argument; | ||||
|  | ||||
| class ProphecySubjectPatchSpec extends ObjectBehavior | ||||
| { | ||||
|     function it_is_a_patch() | ||||
|     { | ||||
|         $this->shouldBeAnInstanceOf('Prophecy\Doubler\ClassPatch\ClassPatchInterface'); | ||||
|     } | ||||
|  | ||||
|     function it_has_priority_of_0() | ||||
|     { | ||||
|         $this->getPriority()->shouldReturn(0); | ||||
|     } | ||||
|  | ||||
|     /** | ||||
|      * @param \Prophecy\Doubler\Generator\Node\ClassNode $node | ||||
|      */ | ||||
|     function it_supports_any_class($node) | ||||
|     { | ||||
|         $this->supports($node)->shouldReturn(true); | ||||
|     } | ||||
|  | ||||
|     /** | ||||
|      * @param \Prophecy\Doubler\Generator\Node\ClassNode $node | ||||
|      */ | ||||
|     function it_forces_class_to_implement_ProphecySubjectInterface($node) | ||||
|     { | ||||
|         $node->addInterface('Prophecy\Prophecy\ProphecySubjectInterface')->shouldBeCalled(); | ||||
|  | ||||
|         $node->addProperty('objectProphecy', 'private')->willReturn(null); | ||||
|         $node->getMethods()->willReturn(array()); | ||||
|         $node->hasMethod(Argument::any())->willReturn(false); | ||||
|         $node->addMethod(Argument::type('Prophecy\Doubler\Generator\Node\MethodNode'))->willReturn(null); | ||||
|         $node->addMethod(Argument::type('Prophecy\Doubler\Generator\Node\MethodNode'))->willReturn(null); | ||||
|  | ||||
|         $this->apply($node); | ||||
|     } | ||||
|  | ||||
|     /** | ||||
|      * @param \Prophecy\Doubler\Generator\Node\ClassNode  $node | ||||
|      * @param \Prophecy\Doubler\Generator\Node\MethodNode $constructor | ||||
|      * @param \Prophecy\Doubler\Generator\Node\MethodNode $method1 | ||||
|      * @param \Prophecy\Doubler\Generator\Node\MethodNode $method2 | ||||
|      * @param \Prophecy\Doubler\Generator\Node\MethodNode $method3 | ||||
|      */ | ||||
|     function it_forces_all_class_methods_except_constructor_to_proxy_calls_into_prophecy_makeCall( | ||||
|         $node, $constructor, $method1, $method2, $method3 | ||||
|     ) | ||||
|     { | ||||
|         $node->addInterface('Prophecy\Prophecy\ProphecySubjectInterface')->willReturn(null); | ||||
|         $node->addProperty('objectProphecy', 'private')->willReturn(null); | ||||
|         $node->hasMethod(Argument::any())->willReturn(false); | ||||
|         $node->addMethod(Argument::type('Prophecy\Doubler\Generator\Node\MethodNode'))->willReturn(null); | ||||
|         $node->addMethod(Argument::type('Prophecy\Doubler\Generator\Node\MethodNode'))->willReturn(null); | ||||
|  | ||||
|         $constructor->getName()->willReturn('__construct'); | ||||
|         $method1->getName()->willReturn('method1'); | ||||
|         $method2->getName()->willReturn('method2'); | ||||
|         $method3->getName()->willReturn('method3'); | ||||
|  | ||||
|         $node->getMethods()->willReturn(array( | ||||
|             'method1' => $method1, | ||||
|             'method2' => $method2, | ||||
|             'method3' => $method3, | ||||
|         )); | ||||
|  | ||||
|         $constructor->setCode(Argument::any())->shouldNotBeCalled(); | ||||
|  | ||||
|         $method1->setCode('return $this->getProphecy()->makeProphecyMethodCall(__FUNCTION__, func_get_args());') | ||||
|             ->shouldBeCalled(); | ||||
|         $method2->setCode('return $this->getProphecy()->makeProphecyMethodCall(__FUNCTION__, func_get_args());') | ||||
|             ->shouldBeCalled(); | ||||
|         $method3->setCode('return $this->getProphecy()->makeProphecyMethodCall(__FUNCTION__, func_get_args());') | ||||
|             ->shouldBeCalled(); | ||||
|  | ||||
|         $this->apply($node); | ||||
|     } | ||||
| } | ||||
| @@ -1,47 +0,0 @@ | ||||
| <?php | ||||
|  | ||||
| namespace spec\Prophecy\Doubler\ClassPatch; | ||||
|  | ||||
| use PhpSpec\ObjectBehavior; | ||||
| use Prophecy\Argument; | ||||
|  | ||||
| class ReflectionClassNewInstancePatchSpec extends ObjectBehavior | ||||
| { | ||||
|     function it_is_a_patch() | ||||
|     { | ||||
|         $this->shouldBeAnInstanceOf('Prophecy\Doubler\ClassPatch\ClassPatchInterface'); | ||||
|     } | ||||
|  | ||||
|     function its_priority_is_50() | ||||
|     { | ||||
|         $this->getPriority()->shouldReturn(50); | ||||
|     } | ||||
|  | ||||
|     /** | ||||
|      * @param \Prophecy\Doubler\Generator\Node\ClassNode $reflectionClassNode | ||||
|      * @param \Prophecy\Doubler\Generator\Node\ClassNode $anotherClassNode | ||||
|      */ | ||||
|     function it_supports_ReflectionClass_only($reflectionClassNode, $anotherClassNode) | ||||
|     { | ||||
|         $reflectionClassNode->getParentClass()->willReturn('ReflectionClass'); | ||||
|         $anotherClassNode->getParentClass()->willReturn('stdClass'); | ||||
|  | ||||
|         $this->supports($reflectionClassNode)->shouldReturn(true); | ||||
|         $this->supports($anotherClassNode)->shouldReturn(false); | ||||
|     } | ||||
|  | ||||
|     /** | ||||
|      * @param \Prophecy\Doubler\Generator\Node\ClassNode    $class | ||||
|      * @param \Prophecy\Doubler\Generator\Node\MethodNode   $method | ||||
|      * @param \Prophecy\Doubler\Generator\Node\ArgumentNode $arg1 | ||||
|      * @param \Prophecy\Doubler\Generator\Node\ArgumentNode $arg2 | ||||
|      */ | ||||
|     function it_makes_all_newInstance_arguments_optional($class, $method, $arg1, $arg2) | ||||
|     { | ||||
|         $class->getMethod('newInstance')->willReturn($method); | ||||
|         $method->getArguments()->willReturn(array($arg1)); | ||||
|         $arg1->setDefault(null)->shouldBeCalled(); | ||||
|  | ||||
|         $this->apply($class); | ||||
|     } | ||||
| } | ||||
| @@ -1,91 +0,0 @@ | ||||
| <?php | ||||
|  | ||||
| namespace spec\Prophecy\Doubler\ClassPatch; | ||||
|  | ||||
| use PhpSpec\ObjectBehavior; | ||||
| use Prophecy\Argument; | ||||
|  | ||||
| class SplFileInfoPatchSpec extends ObjectBehavior | ||||
| { | ||||
|     function it_is_a_patch() | ||||
|     { | ||||
|         $this->shouldBeAnInstanceOf('Prophecy\Doubler\ClassPatch\ClassPatchInterface'); | ||||
|     } | ||||
|  | ||||
|     function its_priority_is_50() | ||||
|     { | ||||
|         $this->getPriority()->shouldReturn(50); | ||||
|     } | ||||
|  | ||||
|     /** | ||||
|      * @param \Prophecy\Doubler\Generator\Node\ClassNode $node | ||||
|      */ | ||||
|     function it_does_not_support_nodes_without_parent_class($node) | ||||
|     { | ||||
|         $node->getParentClass()->willReturn('stdClass'); | ||||
|         $this->supports($node)->shouldReturn(false); | ||||
|     } | ||||
|  | ||||
|     /** | ||||
|      * @param \Prophecy\Doubler\Generator\Node\ClassNode $node | ||||
|      */ | ||||
|     function it_supports_nodes_with_SplFileInfo_as_parent_class($node) | ||||
|     { | ||||
|         $node->getParentClass()->willReturn('SplFileInfo'); | ||||
|         $this->supports($node)->shouldReturn(true); | ||||
|     } | ||||
|  | ||||
|     /** | ||||
|      * @param \Prophecy\Doubler\Generator\Node\ClassNode $node | ||||
|      */ | ||||
|     function it_supports_nodes_with_derivative_of_SplFileInfo_as_parent_class($node) | ||||
|     { | ||||
|         $node->getParentClass()->willReturn('SplFileInfo'); | ||||
|         $this->supports($node)->shouldReturn(true); | ||||
|     } | ||||
|  | ||||
|     /** | ||||
|      * @param \Prophecy\Doubler\Generator\Node\ClassNode $node | ||||
|      */ | ||||
|     function it_adds_a_method_to_node_if_not_exists($node) | ||||
|     { | ||||
|         $node->hasMethod('__construct')->willReturn(false); | ||||
|         $node->addMethod(Argument::any())->shouldBeCalled(); | ||||
|         $node->getParentClass()->shouldBeCalled(); | ||||
|  | ||||
|         $this->apply($node); | ||||
|     } | ||||
|  | ||||
|     /** | ||||
|      * @param \Prophecy\Doubler\Generator\Node\ClassNode  $node | ||||
|      * @param \Prophecy\Doubler\Generator\Node\MethodNode $method | ||||
|      */ | ||||
|     function it_updates_existing_method_if_found($node, $method) | ||||
|     { | ||||
|         $node->hasMethod('__construct')->willReturn(true); | ||||
|         $node->getMethod('__construct')->willReturn($method); | ||||
|         $node->getParentClass()->shouldBeCalled(); | ||||
|  | ||||
|         $method->useParentCode()->shouldBeCalled(); | ||||
|  | ||||
|         $this->apply($node); | ||||
|     } | ||||
|  | ||||
|     /** | ||||
|      * @param \Prophecy\Doubler\Generator\Node\ClassNode  $node | ||||
|      * @param \Prophecy\Doubler\Generator\Node\MethodNode $method | ||||
|      */ | ||||
|     function it_should_not_supply_a_file_for_a_directory_iterator($node, $method) | ||||
|     { | ||||
|         $node->hasMethod('__construct')->willReturn(true); | ||||
|         $node->getMethod('__construct')->willReturn($method); | ||||
|         $node->getParentClass()->willReturn('DirectoryIterator'); | ||||
|  | ||||
|         $method->setCode(Argument::that(function($value) { | ||||
|             return strpos($value, '.php') === false; | ||||
|         }))->shouldBeCalled(); | ||||
|  | ||||
|         $this->apply($node); | ||||
|     } | ||||
|  | ||||
| } | ||||
| @@ -1,61 +0,0 @@ | ||||
| <?php | ||||
|  | ||||
| namespace spec\Prophecy\Doubler\ClassPatch; | ||||
|  | ||||
| use PhpSpec\ObjectBehavior; | ||||
| use Prophecy\Argument; | ||||
|  | ||||
| class TraversablePatchSpec extends ObjectBehavior | ||||
| { | ||||
|     function it_is_a_patch() | ||||
|     { | ||||
|         $this->shouldBeAnInstanceOf('Prophecy\Doubler\ClassPatch\ClassPatchInterface'); | ||||
|     } | ||||
|  | ||||
|     /** | ||||
|      * @param \Prophecy\Doubler\Generator\Node\ClassNode $node | ||||
|      */ | ||||
|     function it_supports_class_that_implements_only_Traversable($node) | ||||
|     { | ||||
|         $node->getInterfaces()->willReturn(array('Traversable')); | ||||
|  | ||||
|         $this->supports($node)->shouldReturn(true); | ||||
|     } | ||||
|  | ||||
|     /** | ||||
|      * @param \Prophecy\Doubler\Generator\Node\ClassNode $node | ||||
|      */ | ||||
|     function it_does_not_support_class_that_implements_Iterator($node) | ||||
|     { | ||||
|         $node->getInterfaces()->willReturn(array('Traversable', 'Iterator')); | ||||
|  | ||||
|         $this->supports($node)->shouldReturn(false); | ||||
|     } | ||||
|  | ||||
|     /** | ||||
|      * @param \Prophecy\Doubler\Generator\Node\ClassNode $node | ||||
|      */ | ||||
|     function it_does_not_support_class_that_implements_IteratorAggregate($node) | ||||
|     { | ||||
|         $node->getInterfaces()->willReturn(array('Traversable', 'IteratorAggregate')); | ||||
|  | ||||
|         $this->supports($node)->shouldReturn(false); | ||||
|     } | ||||
|  | ||||
|     function it_has_100_priority() | ||||
|     { | ||||
|         $this->getPriority()->shouldReturn(100); | ||||
|     } | ||||
|  | ||||
|     /** | ||||
|      * @param \Prophecy\Doubler\Generator\Node\ClassNode $node | ||||
|      */ | ||||
|     function it_forces_node_to_implement_IteratorAggregate($node) | ||||
|     { | ||||
|         $node->addInterface('Iterator')->shouldBeCalled(); | ||||
|  | ||||
|         $node->addMethod(Argument::type('Prophecy\Doubler\Generator\Node\MethodNode'))->willReturn(null); | ||||
|  | ||||
|         $this->apply($node); | ||||
|     } | ||||
| } | ||||
| @@ -1,122 +0,0 @@ | ||||
| <?php | ||||
|  | ||||
| namespace spec\Prophecy\Doubler; | ||||
|  | ||||
| use PhpSpec\ObjectBehavior; | ||||
| use Prophecy\Argument; | ||||
|  | ||||
| class DoublerSpec extends ObjectBehavior | ||||
| { | ||||
|     /** | ||||
|      * @param \Prophecy\Doubler\Generator\ClassMirror  $mirror | ||||
|      * @param \Prophecy\Doubler\Generator\ClassCreator $creator | ||||
|      * @param \Prophecy\Doubler\NameGenerator          $namer | ||||
|      */ | ||||
|     function let($mirror, $creator, $namer) | ||||
|     { | ||||
|         $this->beConstructedWith($mirror, $creator, $namer); | ||||
|     } | ||||
|  | ||||
|     function it_does_not_have_patches_by_default() | ||||
|     { | ||||
|         $this->getClassPatches()->shouldHaveCount(0); | ||||
|     } | ||||
|  | ||||
|     /** | ||||
|      * @param \Prophecy\Doubler\ClassPatch\ClassPatchInterface $patch | ||||
|      */ | ||||
|     function its_registerClassPatch_adds_a_patch_to_the_doubler($patch) | ||||
|     { | ||||
|         $this->registerClassPatch($patch); | ||||
|         $this->getClassPatches()->shouldReturn(array($patch)); | ||||
|     } | ||||
|  | ||||
|     /** | ||||
|      * @param \Prophecy\Doubler\ClassPatch\ClassPatchInterface $alt1 | ||||
|      * @param \Prophecy\Doubler\ClassPatch\ClassPatchInterface $alt2 | ||||
|      * @param \Prophecy\Doubler\ClassPatch\ClassPatchInterface $alt3 | ||||
|      * @param \Prophecy\Doubler\ClassPatch\ClassPatchInterface $alt4 | ||||
|      */ | ||||
|     function its_getClassPatches_sorts_patches_by_priority($alt1, $alt2, $alt3, $alt4) | ||||
|     { | ||||
|         $alt1->getPriority()->willReturn(2); | ||||
|         $alt2->getPriority()->willReturn(50); | ||||
|         $alt3->getPriority()->willReturn(10); | ||||
|         $alt4->getPriority()->willReturn(0); | ||||
|  | ||||
|         $this->registerClassPatch($alt1); | ||||
|         $this->registerClassPatch($alt2); | ||||
|         $this->registerClassPatch($alt3); | ||||
|         $this->registerClassPatch($alt4); | ||||
|  | ||||
|         $this->getClassPatches()->shouldReturn(array($alt2, $alt3, $alt1, $alt4)); | ||||
|     } | ||||
|  | ||||
|     /** | ||||
|      * @param \Prophecy\Doubler\ClassPatch\ClassPatchInterface $alt1 | ||||
|      * @param \Prophecy\Doubler\ClassPatch\ClassPatchInterface $alt2 | ||||
|      * @param \ReflectionClass                                 $class | ||||
|      * @param \ReflectionClass                                 $interface1 | ||||
|      * @param \ReflectionClass                                 $interface2 | ||||
|      * @param \Prophecy\Doubler\Generator\Node\ClassNode       $node | ||||
|      */ | ||||
|     function its_double_mirrors_alterates_and_instantiates_provided_class( | ||||
|         $mirror, $creator, $namer, $alt1, $alt2, $class, $interface1, $interface2, $node | ||||
|     ) | ||||
|     { | ||||
|         $mirror->reflect($class, array($interface1, $interface2))->willReturn($node); | ||||
|         $alt1->supports($node)->willReturn(true); | ||||
|         $alt2->supports($node)->willReturn(false); | ||||
|         $alt1->getPriority()->willReturn(1); | ||||
|         $alt2->getPriority()->willReturn(2); | ||||
|         $namer->name($class, array($interface1, $interface2))->willReturn('SplStack'); | ||||
|         $class->getName()->willReturn('stdClass'); | ||||
|         $interface1->getName()->willReturn('ArrayAccess'); | ||||
|         $interface2->getName()->willReturn('Iterator'); | ||||
|  | ||||
|         $alt1->apply($node)->shouldBeCalled(); | ||||
|         $alt2->apply($node)->shouldNotBeCalled(); | ||||
|         $creator->create('SplStack', $node)->shouldBeCalled(); | ||||
|  | ||||
|         $this->registerClassPatch($alt1); | ||||
|         $this->registerClassPatch($alt2); | ||||
|  | ||||
|         $this->double($class, array($interface1, $interface2)) | ||||
|             ->shouldReturnAnInstanceOf('SplStack'); | ||||
|     } | ||||
|  | ||||
|     /** | ||||
|      * @param \ReflectionClass                           $class | ||||
|      * @param \Prophecy\Doubler\Generator\Node\ClassNode $node | ||||
|      */ | ||||
|     function it_double_instantiates_a_class_with_constructor_argument($mirror, $class, $node, $namer) | ||||
|     { | ||||
|         $class->getName()->willReturn('ReflectionClass'); | ||||
|         $mirror->reflect($class, array())->willReturn($node); | ||||
|         $namer->name($class, array())->willReturn('ReflectionClass'); | ||||
|  | ||||
|         $double = $this->double($class, array(), array('stdClass')); | ||||
|         $double->shouldBeAnInstanceOf('ReflectionClass'); | ||||
|         $double->getName()->shouldReturn('stdClass'); | ||||
|     } | ||||
|  | ||||
|     /** | ||||
|      * @param \ReflectionClass                           $class | ||||
|      * @param \Prophecy\Doubler\Generator\Node\ClassNode $node | ||||
|      */ | ||||
|     function it_can_instantiate_class_with_final_constructor($mirror, $class, $node, $namer) | ||||
|     { | ||||
|         $class->getName()->willReturn('spec\Prophecy\Doubler\WithFinalConstructor'); | ||||
|         $mirror->reflect($class, array())->willReturn($node); | ||||
|         $namer->name($class, array())->willReturn('spec\Prophecy\Doubler\WithFinalConstructor'); | ||||
|  | ||||
|         $double = $this->double($class, array()); | ||||
|  | ||||
|         $double->shouldBeAnInstanceOf('spec\Prophecy\Doubler\WithFinalConstructor'); | ||||
|     } | ||||
| } | ||||
|  | ||||
| class WithFinalConstructor | ||||
| { | ||||
|     final public function __construct() {} | ||||
| } | ||||
| @@ -1,186 +0,0 @@ | ||||
| <?php | ||||
|  | ||||
| namespace spec\Prophecy\Doubler\Generator; | ||||
|  | ||||
| use PhpSpec\ObjectBehavior; | ||||
|  | ||||
| class ClassCodeGeneratorSpec extends ObjectBehavior | ||||
| { | ||||
|     /** | ||||
|      * @param \Prophecy\Doubler\Generator\Node\ClassNode    $class | ||||
|      * @param \Prophecy\Doubler\Generator\Node\MethodNode   $method1 | ||||
|      * @param \Prophecy\Doubler\Generator\Node\MethodNode   $method2 | ||||
|      * @param \Prophecy\Doubler\Generator\Node\MethodNode   $method3 | ||||
|      * @param \Prophecy\Doubler\Generator\Node\ArgumentNode $argument11 | ||||
|      * @param \Prophecy\Doubler\Generator\Node\ArgumentNode $argument12 | ||||
|      * @param \Prophecy\Doubler\Generator\Node\ArgumentNode $argument21 | ||||
|      * @param \Prophecy\Doubler\Generator\Node\ArgumentNode $argument31 | ||||
|      */ | ||||
|     function it_generates_proper_php_code_for_specific_ClassNode( | ||||
|         $class, $method1, $method2, $method3, $argument11, $argument12, $argument21, $argument31 | ||||
|     ) | ||||
|     { | ||||
|         $class->getParentClass()->willReturn('RuntimeException'); | ||||
|         $class->getInterfaces()->willReturn(array( | ||||
|             'Prophecy\Doubler\Generator\MirroredInterface', 'ArrayAccess', 'ArrayIterator' | ||||
|         )); | ||||
|         $class->getProperties()->willReturn(array('name' => 'public', 'email' => 'private')); | ||||
|         $class->getMethods()->willReturn(array($method1, $method2, $method3)); | ||||
|  | ||||
|         $method1->getName()->willReturn('getName'); | ||||
|         $method1->getVisibility()->willReturn('public'); | ||||
|         $method1->returnsReference()->willReturn(false); | ||||
|         $method1->isStatic()->willReturn(true); | ||||
|         $method1->getArguments()->willReturn(array($argument11, $argument12)); | ||||
|         $method1->getCode()->willReturn('return $this->name;'); | ||||
|  | ||||
|         $method2->getName()->willReturn('getEmail'); | ||||
|         $method2->getVisibility()->willReturn('protected'); | ||||
|         $method2->returnsReference()->willReturn(false); | ||||
|         $method2->isStatic()->willReturn(false); | ||||
|         $method2->getArguments()->willReturn(array($argument21)); | ||||
|         $method2->getCode()->willReturn('return $this->email;'); | ||||
|  | ||||
|         $method3->getName()->willReturn('getRefValue'); | ||||
|         $method3->getVisibility()->willReturn('public'); | ||||
|         $method3->returnsReference()->willReturn(true); | ||||
|         $method3->isStatic()->willReturn(false); | ||||
|         $method3->getArguments()->willReturn(array($argument31)); | ||||
|         $method3->getCode()->willReturn('return $this->refValue;'); | ||||
|  | ||||
|         $argument11->getName()->willReturn('fullname'); | ||||
|         $argument11->getTypeHint()->willReturn('array'); | ||||
|         $argument11->isOptional()->willReturn(true); | ||||
|         $argument11->getDefault()->willReturn(null); | ||||
|         $argument11->isPassedByReference()->willReturn(false); | ||||
|  | ||||
|         $argument12->getName()->willReturn('class'); | ||||
|         $argument12->getTypeHint()->willReturn('ReflectionClass'); | ||||
|         $argument12->isOptional()->willReturn(false); | ||||
|         $argument12->isPassedByReference()->willReturn(false); | ||||
|  | ||||
|         $argument21->getName()->willReturn('default'); | ||||
|         $argument21->getTypeHint()->willReturn(null); | ||||
|         $argument21->isOptional()->willReturn(true); | ||||
|         $argument21->getDefault()->willReturn('ever.zet@gmail.com'); | ||||
|         $argument21->isPassedByReference()->willReturn(false); | ||||
|  | ||||
|         $argument31->getName()->willReturn('refValue'); | ||||
|         $argument31->getTypeHint()->willReturn(null); | ||||
|         $argument31->isOptional()->willReturn(false); | ||||
|         $argument31->getDefault()->willReturn(); | ||||
|         $argument31->isPassedByReference()->willReturn(false); | ||||
|  | ||||
|         $code = $this->generate('CustomClass', $class); | ||||
|         $expected = <<<'PHP' | ||||
| namespace  { | ||||
| class CustomClass extends \RuntimeException implements \Prophecy\Doubler\Generator\MirroredInterface, \ArrayAccess, \ArrayIterator { | ||||
| public $name; | ||||
| private $email; | ||||
|  | ||||
| public static function getName(array $fullname = NULL, \ReflectionClass $class) { | ||||
| return $this->name; | ||||
| } | ||||
| protected  function getEmail( $default = 'ever.zet@gmail.com') { | ||||
| return $this->email; | ||||
| } | ||||
| public  function &getRefValue( $refValue) { | ||||
| return $this->refValue; | ||||
| } | ||||
|  | ||||
| } | ||||
| } | ||||
| PHP; | ||||
|         $expected = strtr($expected, array("\r\n" => "\n", "\r" => "\n")); | ||||
|         $code->shouldBe($expected); | ||||
|     } | ||||
|  | ||||
|     /** | ||||
|      * @param \Prophecy\Doubler\Generator\Node\ClassNode    $class | ||||
|      * @param \Prophecy\Doubler\Generator\Node\MethodNode   $method | ||||
|      * @param \Prophecy\Doubler\Generator\Node\ArgumentNode $argument | ||||
|      */ | ||||
|     function it_overrides_properly_methods_with_args_passed_by_reference( | ||||
|         $class, $method, $argument | ||||
|     ) | ||||
|     { | ||||
|         $class->getParentClass()->willReturn('RuntimeException'); | ||||
|         $class->getInterfaces()->willReturn(array('Prophecy\Doubler\Generator\MirroredInterface')); | ||||
|         $class->getProperties()->willReturn(array()); | ||||
|         $class->getMethods()->willReturn(array($method)); | ||||
|  | ||||
|         $method->getName()->willReturn('getName'); | ||||
|         $method->getVisibility()->willReturn('public'); | ||||
|         $method->isStatic()->willReturn(false); | ||||
|         $method->getArguments()->willReturn(array($argument)); | ||||
|         $method->returnsReference()->willReturn(false); | ||||
|         $method->getCode()->willReturn('return $this->name;'); | ||||
|  | ||||
|         $argument->getName()->willReturn('fullname'); | ||||
|         $argument->getTypeHint()->willReturn('array'); | ||||
|         $argument->isOptional()->willReturn(true); | ||||
|         $argument->getDefault()->willReturn(null); | ||||
|         $argument->isPassedByReference()->willReturn(true); | ||||
|  | ||||
|         $code = $this->generate('CustomClass', $class); | ||||
|         $expected =<<<'PHP' | ||||
| namespace  { | ||||
| class CustomClass extends \RuntimeException implements \Prophecy\Doubler\Generator\MirroredInterface { | ||||
|  | ||||
| public  function getName(array &$fullname = NULL) { | ||||
| return $this->name; | ||||
| } | ||||
|  | ||||
| } | ||||
| } | ||||
| PHP; | ||||
|         $expected = strtr($expected, array("\r\n" => "\n", "\r" => "\n")); | ||||
|         $code->shouldBe($expected); | ||||
|     } | ||||
|  | ||||
|     /** | ||||
|      * @param \Prophecy\Doubler\Generator\Node\ClassNode $class | ||||
|      */ | ||||
|     function it_generates_empty_class_for_empty_ClassNode($class) | ||||
|     { | ||||
|         $class->getParentClass()->willReturn('stdClass'); | ||||
|         $class->getInterfaces()->willReturn(array('Prophecy\Doubler\Generator\MirroredInterface')); | ||||
|         $class->getProperties()->willReturn(array()); | ||||
|         $class->getMethods()->willReturn(array()); | ||||
|  | ||||
|         $code = $this->generate('CustomClass', $class); | ||||
|         $expected =<<<'PHP' | ||||
| namespace  { | ||||
| class CustomClass extends \stdClass implements \Prophecy\Doubler\Generator\MirroredInterface { | ||||
|  | ||||
|  | ||||
| } | ||||
| } | ||||
| PHP; | ||||
|         $expected = strtr($expected, array("\r\n" => "\n", "\r" => "\n")); | ||||
|         $code->shouldBe($expected); | ||||
|     } | ||||
|  | ||||
|     /** | ||||
|      * @param \Prophecy\Doubler\Generator\Node\ClassNode $class | ||||
|      */ | ||||
|     function it_wraps_class_in_namespace_if_it_is_namespaced($class) | ||||
|     { | ||||
|         $class->getParentClass()->willReturn('stdClass'); | ||||
|         $class->getInterfaces()->willReturn(array('Prophecy\Doubler\Generator\MirroredInterface')); | ||||
|         $class->getProperties()->willReturn(array()); | ||||
|         $class->getMethods()->willReturn(array()); | ||||
|  | ||||
|         $code = $this->generate('My\Awesome\CustomClass', $class); | ||||
|         $expected =<<<'PHP' | ||||
| namespace My\Awesome { | ||||
| class CustomClass extends \stdClass implements \Prophecy\Doubler\Generator\MirroredInterface { | ||||
|  | ||||
|  | ||||
| } | ||||
| } | ||||
| PHP; | ||||
|         $expected = strtr($expected, array("\r\n" => "\n", "\r" => "\n")); | ||||
|         $code->shouldBe($expected); | ||||
|     } | ||||
| } | ||||
| @@ -1,44 +0,0 @@ | ||||
| <?php | ||||
|  | ||||
| namespace spec\Prophecy\Doubler\Generator; | ||||
|  | ||||
| use PhpSpec\ObjectBehavior; | ||||
|  | ||||
| class ClassCreatorSpec extends ObjectBehavior | ||||
| { | ||||
|     /** | ||||
|      * @param \Prophecy\Doubler\Generator\ClassCodeGenerator $generator | ||||
|      */ | ||||
|     function let($generator) | ||||
|     { | ||||
|         $this->beConstructedWith($generator); | ||||
|     } | ||||
|  | ||||
|     /** | ||||
|      * @param \Prophecy\Doubler\Generator\Node\ClassNode $class | ||||
|      */ | ||||
|     function it_evaluates_code_generated_by_ClassCodeGenerator($generator, $class) | ||||
|     { | ||||
|         $generator->generate('stdClass', $class)->shouldBeCalled()->willReturn( | ||||
|             'return 42;' | ||||
|         ); | ||||
|  | ||||
|         $this->create('stdClass', $class)->shouldReturn(42); | ||||
|     } | ||||
|  | ||||
|     /** | ||||
|      * @param \Prophecy\Doubler\Generator\Node\ClassNode $class | ||||
|      */ | ||||
|     function it_throws_an_exception_if_class_does_not_exist_after_evaluation($generator, $class) | ||||
|     { | ||||
|         $generator->generate('CustomClass', $class)->shouldBeCalled()->willReturn( | ||||
|             'return 42;' | ||||
|         ); | ||||
|  | ||||
|         $class->getParentClass()->willReturn('stdClass'); | ||||
|         $class->getInterfaces()->willReturn(array('Interface1', 'Interface2')); | ||||
|  | ||||
|         $this->shouldThrow('Prophecy\Exception\Doubler\ClassCreatorException') | ||||
|             ->duringCreate('CustomClass', $class); | ||||
|     } | ||||
| } | ||||
| @@ -1,554 +0,0 @@ | ||||
| <?php | ||||
|  | ||||
| namespace spec\Prophecy\Doubler\Generator; | ||||
|  | ||||
| use PhpSpec\ObjectBehavior; | ||||
| use I\Simply; | ||||
|  | ||||
| use ReflectionClass; | ||||
| use ReflectionMethod; | ||||
| use ReflectionParameter; | ||||
|  | ||||
| class ClassMirrorSpec extends ObjectBehavior | ||||
| { | ||||
|     /** | ||||
|      * @param ReflectionClass  $class | ||||
|      * @param ReflectionMethod $method1 | ||||
|      * @param ReflectionMethod $method2 | ||||
|      * @param ReflectionMethod $method3 | ||||
|      */ | ||||
|     function it_reflects_a_class_by_mirroring_all_its_public_methods( | ||||
|         $class, $method1, $method2, $method3 | ||||
|     ) | ||||
|     { | ||||
|         $class->getName()->willReturn('Custom\ClassName'); | ||||
|         $class->isInterface()->willReturn(false); | ||||
|         $class->isFinal()->willReturn(false); | ||||
|         $class->getMethods(ReflectionMethod::IS_ABSTRACT)->willReturn(array()); | ||||
|         $class->getMethods(ReflectionMethod::IS_PUBLIC)->willReturn(array( | ||||
|             $method1, $method2, $method3 | ||||
|         )); | ||||
|  | ||||
|         $method1->getName()->willReturn('getName'); | ||||
|         $method2->getName()->willReturn('isPublic'); | ||||
|         $method3->getName()->willReturn('isAbstract'); | ||||
|  | ||||
|         $method1->isFinal()->willReturn(false); | ||||
|         $method2->isFinal()->willReturn(false); | ||||
|         $method3->isFinal()->willReturn(false); | ||||
|  | ||||
|         $method1->isProtected()->willReturn(false); | ||||
|         $method2->isProtected()->willReturn(false); | ||||
|         $method3->isProtected()->willReturn(false); | ||||
|  | ||||
|         $method1->isStatic()->willReturn(false); | ||||
|         $method2->isStatic()->willReturn(false); | ||||
|         $method3->isStatic()->willReturn(false); | ||||
|  | ||||
|         $method1->returnsReference()->willReturn(false); | ||||
|         $method2->returnsReference()->willReturn(false); | ||||
|         $method3->returnsReference()->willReturn(false); | ||||
|  | ||||
|         $method1->getParameters()->willReturn(array()); | ||||
|         $method2->getParameters()->willReturn(array()); | ||||
|         $method3->getParameters()->willReturn(array()); | ||||
|  | ||||
|         $classNode   = $this->reflect($class, array()); | ||||
|         $classNode->shouldBeAnInstanceOf('Prophecy\Doubler\Generator\Node\ClassNode'); | ||||
|         $classNode->getParentClass()->shouldReturn('Custom\ClassName'); | ||||
|  | ||||
|         $methodNodes = $classNode->getMethods(); | ||||
|         $methodNodes->shouldHaveCount(3); | ||||
|  | ||||
|         $classNode->hasMethod('getName')->shouldReturn(true); | ||||
|         $classNode->hasMethod('isPublic')->shouldReturn(true); | ||||
|         $classNode->hasMethod('isAbstract')->shouldReturn(true); | ||||
|     } | ||||
|  | ||||
|     /** | ||||
|      * @param ReflectionClass     $class | ||||
|      * @param ReflectionMethod    $method | ||||
|      * @param ReflectionParameter $parameter | ||||
|      */ | ||||
|     function it_changes_argument_names_if_they_are_varying($class, $method, $parameter) | ||||
|     { | ||||
|  | ||||
|         $class->getName()->willReturn('Custom\ClassName'); | ||||
|         $class->isInterface()->willReturn(false); | ||||
|         $class->isFinal()->willReturn(false); | ||||
|         $class->getMethods(ReflectionMethod::IS_PUBLIC)->willReturn(array($method)); | ||||
|         $class->getMethods(ReflectionMethod::IS_ABSTRACT)->willReturn(array()); | ||||
|  | ||||
|         $method->getParameters()->willReturn(array($parameter)); | ||||
|         $method->getName()->willReturn('methodName'); | ||||
|         $method->isFinal()->willReturn(false); | ||||
|         $method->isProtected()->willReturn(false); | ||||
|         $method->isStatic()->willReturn(false); | ||||
|         $method->returnsReference()->willReturn(false); | ||||
|  | ||||
|         $parameter->getName()->willReturn('...'); | ||||
|         $parameter->isDefaultValueAvailable()->willReturn(true); | ||||
|         $parameter->getDefaultValue()->willReturn(null); | ||||
|         $parameter->isPassedByReference()->willReturn(false); | ||||
|         $parameter->getClass()->willReturn($class); | ||||
|  | ||||
|         $classNode = $this->reflect($class, array()); | ||||
|  | ||||
|         $methodNodes = $classNode->getMethods(); | ||||
|  | ||||
|         $argumentNodes = $methodNodes['methodName']->getArguments(); | ||||
|         $argumentNode = $argumentNodes[0]; | ||||
|  | ||||
|         $argumentNode->getName()->shouldReturn('__dot_dot_dot__'); | ||||
|     } | ||||
|  | ||||
|     /** | ||||
|      * @param ReflectionClass  $class | ||||
|      * @param ReflectionMethod $method | ||||
|      */ | ||||
|     function it_reflects_protected_abstract_methods($class, $method) | ||||
|     { | ||||
|         $class->getName()->willReturn('Custom\ClassName'); | ||||
|         $class->isInterface()->willReturn(false); | ||||
|         $class->isFinal()->willReturn(false); | ||||
|         $class->getMethods(ReflectionMethod::IS_ABSTRACT)->willReturn(array($method)); | ||||
|         $class->getMethods(ReflectionMethod::IS_PUBLIC)->willReturn(array()); | ||||
|  | ||||
|         $method->isProtected()->willReturn(true); | ||||
|         $method->isStatic()->willReturn(false); | ||||
|         $method->getParameters()->willReturn(array()); | ||||
|         $method->getName()->willReturn('innerDetail'); | ||||
|         $method->returnsReference()->willReturn(false); | ||||
|  | ||||
|  | ||||
|         $classNode   = $this->reflect($class, array()); | ||||
|         $classNode->shouldBeAnInstanceOf('Prophecy\Doubler\Generator\Node\ClassNode'); | ||||
|         $classNode->getParentClass()->shouldReturn('Custom\ClassName'); | ||||
|  | ||||
|         $methodNodes = $classNode->getMethods(); | ||||
|         $methodNodes->shouldHaveCount(1); | ||||
|  | ||||
|         $methodNodes['innerDetail']->getVisibility()->shouldReturn('protected'); | ||||
|     } | ||||
|  | ||||
|     /** | ||||
|      * @param ReflectionClass  $class | ||||
|      * @param ReflectionMethod $method | ||||
|      */ | ||||
|     function it_reflects_public_static_methods($class, $method) | ||||
|     { | ||||
|         $class->getName()->willReturn('Custom\ClassName'); | ||||
|         $class->isInterface()->willReturn(false); | ||||
|         $class->isFinal()->willReturn(false); | ||||
|         $class->getMethods(ReflectionMethod::IS_ABSTRACT)->willReturn(array($method)); | ||||
|         $class->getMethods(ReflectionMethod::IS_PUBLIC)->willReturn(array()); | ||||
|  | ||||
|         $method->isProtected()->willReturn(true); | ||||
|         $method->isStatic()->willReturn(true); | ||||
|         $method->getParameters()->willReturn(array()); | ||||
|         $method->getName()->willReturn('innerDetail'); | ||||
|         $method->returnsReference()->willReturn(false); | ||||
|  | ||||
|         $classNode   = $this->reflect($class, array()); | ||||
|         $classNode->shouldBeAnInstanceOf('Prophecy\Doubler\Generator\Node\ClassNode'); | ||||
|         $classNode->getParentClass()->shouldReturn('Custom\ClassName'); | ||||
|  | ||||
|         $methodNodes = $classNode->getMethods(); | ||||
|         $methodNodes->shouldHaveCount(1); | ||||
|  | ||||
|         $methodNodes['innerDetail']->getVisibility()->shouldReturn('protected'); | ||||
|         $methodNodes['innerDetail']->isStatic()->shouldReturn(true); | ||||
|     } | ||||
|  | ||||
|     /** | ||||
|      * @param ReflectionClass     $class | ||||
|      * @param ReflectionMethod    $method | ||||
|      * @param ReflectionParameter $param1 | ||||
|      * @param ReflectionParameter $param2 | ||||
|      * @param ReflectionClass     $typeHint | ||||
|      * @param ReflectionParameter $param3 | ||||
|      */ | ||||
|     function it_properly_reads_methods_arguments_with_types( | ||||
|         $class, $method, $param1, $param2, $typeHint, $param3 | ||||
|     ) | ||||
|     { | ||||
|         $class->getName()->willReturn('Custom\ClassName'); | ||||
|         $class->isInterface()->willReturn(false); | ||||
|         $class->isFinal()->willReturn(false); | ||||
|         $class->getMethods(ReflectionMethod::IS_ABSTRACT)->willReturn(array()); | ||||
|         $class->getMethods(ReflectionMethod::IS_PUBLIC)->willReturn(array($method)); | ||||
|  | ||||
|         $method->getName()->willReturn('methodWithArgs'); | ||||
|         $method->isFinal()->willReturn(false); | ||||
|         $method->isProtected()->willReturn(true); | ||||
|         $method->isStatic()->willReturn(false); | ||||
|         $method->returnsReference()->willReturn(false); | ||||
|         $method->getParameters()->willReturn(array($param1, $param2, $param3)); | ||||
|  | ||||
|         $param1->getName()->willReturn('arg_1'); | ||||
|         $param1->isArray()->willReturn(true); | ||||
|         $param1->getClass()->willReturn(null); | ||||
|         $param1->isDefaultValueAvailable()->willReturn(true); | ||||
|         $param1->isPassedByReference()->willReturn(false); | ||||
|         $param1->allowsNull()->willReturn(false); | ||||
|         $param1->getDefaultValue()->willReturn(array()); | ||||
|  | ||||
|         $param2->getName()->willReturn('arg2'); | ||||
|         $param2->isArray()->willReturn(false); | ||||
|         $param2->getClass()->willReturn($typeHint); | ||||
|         $param2->isDefaultValueAvailable()->willReturn(false); | ||||
|         $param2->isOptional()->willReturn(false); | ||||
|         $param2->isPassedByReference()->willReturn(false); | ||||
|         $param2->allowsNull()->willReturn(false); | ||||
|         $typeHint->getName()->willReturn('ArrayAccess'); | ||||
|  | ||||
|         $param3->getName()->willReturn('arg_3'); | ||||
|         $param3->isArray()->willReturn(false); | ||||
|         if (version_compare(PHP_VERSION, '5.4', '>=')) { | ||||
|             $param3->isCallable()->willReturn(true); | ||||
|         } | ||||
|         $param3->getClass()->willReturn(null); | ||||
|         $param3->isOptional()->willReturn(false); | ||||
|         $param3->isDefaultValueAvailable()->willReturn(false); | ||||
|         $param3->isPassedByReference()->willReturn(false); | ||||
|         $param3->allowsNull()->willReturn(true); | ||||
|  | ||||
|         $classNode   = $this->reflect($class, array()); | ||||
|         $methodNodes = $classNode->getMethods(); | ||||
|         $argNodes    = $methodNodes['methodWithArgs']->getArguments(); | ||||
|  | ||||
|         $argNodes[0]->getName()->shouldReturn('arg_1'); | ||||
|         $argNodes[0]->getTypeHint()->shouldReturn('array'); | ||||
|         $argNodes[0]->isOptional()->shouldReturn(true); | ||||
|         $argNodes[0]->getDefault()->shouldReturn(array()); | ||||
|  | ||||
|         $argNodes[1]->getName()->shouldReturn('arg2'); | ||||
|         $argNodes[1]->getTypeHint()->shouldReturn('ArrayAccess'); | ||||
|         $argNodes[1]->isOptional()->shouldReturn(false); | ||||
|  | ||||
|         $argNodes[2]->getName()->shouldReturn('arg_3'); | ||||
|         if (version_compare(PHP_VERSION, '5.4', '>=')) { | ||||
|             $argNodes[2]->getTypeHint()->shouldReturn('callable'); | ||||
|             $argNodes[2]->isOptional()->shouldReturn(true); | ||||
|             $argNodes[2]->getDefault()->shouldReturn(null); | ||||
|         } else { | ||||
|             $argNodes[2]->isOptional()->shouldReturn(false); | ||||
|         } | ||||
|     } | ||||
|  | ||||
|     /** | ||||
|      * @param ReflectionClass     $class | ||||
|      * @param ReflectionMethod    $method | ||||
|      * @param ReflectionParameter $param1 | ||||
|      */ | ||||
|     function it_marks_required_args_without_types_as_not_optional( | ||||
|         $class, $method, $param1 | ||||
|     ) | ||||
|     { | ||||
|         $class->getName()->willReturn('Custom\ClassName'); | ||||
|         $class->isInterface()->willReturn(false); | ||||
|         $class->isFinal()->willReturn(false); | ||||
|         $class->getMethods(ReflectionMethod::IS_ABSTRACT)->willReturn(array()); | ||||
|         $class->getMethods(ReflectionMethod::IS_PUBLIC)->willReturn(array($method)); | ||||
|  | ||||
|         $method->getName()->willReturn('methodWithArgs'); | ||||
|         $method->isFinal()->willReturn(false); | ||||
|         $method->isProtected()->willReturn(false); | ||||
|         $method->isStatic()->willReturn(false); | ||||
|         $method->returnsReference()->willReturn(false); | ||||
|         $method->getParameters()->willReturn(array($param1)); | ||||
|  | ||||
|         $param1->getName()->willReturn('arg_1'); | ||||
|         $param1->isArray()->willReturn(false); | ||||
|         if (version_compare(PHP_VERSION, '5.4', '>=')) { | ||||
|             $param1->isCallable()->willReturn(false); | ||||
|         } | ||||
|         $param1->getClass()->willReturn(null); | ||||
|         $param1->isDefaultValueAvailable()->willReturn(false); | ||||
|         $param1->isOptional()->willReturn(false); | ||||
|         $param1->isPassedByReference()->willReturn(false); | ||||
|         $param1->allowsNull()->willReturn(true); | ||||
|         if (defined('HHVM_VERSION')) { | ||||
|             $param1->getTypehintText()->willReturn(null); | ||||
|         } | ||||
|  | ||||
|         $classNode   = $this->reflect($class, array()); | ||||
|         $methodNodes = $classNode->getMethods(); | ||||
|         $argNodes    = $methodNodes['methodWithArgs']->getArguments(); | ||||
|  | ||||
|         $argNodes[0]->isOptional()->shouldReturn(false); | ||||
|     } | ||||
|  | ||||
|     /** | ||||
|      * @param ReflectionClass     $class | ||||
|      * @param ReflectionMethod    $method | ||||
|      * @param ReflectionParameter $param1 | ||||
|      * @param ReflectionParameter $param2 | ||||
|      * @param ReflectionClass     $typeHint | ||||
|      */ | ||||
|     function it_marks_passed_by_reference_args_as_passed_by_reference( | ||||
|         $class, $method, $param1, $param2, $typeHint | ||||
|     ) | ||||
|     { | ||||
|         $class->getName()->willReturn('Custom\ClassName'); | ||||
|         $class->isInterface()->willReturn(false); | ||||
|         $class->isFinal()->willReturn(false); | ||||
|         $class->getMethods(ReflectionMethod::IS_ABSTRACT)->willReturn(array()); | ||||
|         $class->getMethods(ReflectionMethod::IS_PUBLIC)->willReturn(array($method)); | ||||
|  | ||||
|         $method->getName()->willReturn('methodWithArgs'); | ||||
|         $method->isFinal()->willReturn(false); | ||||
|         $method->isProtected()->willReturn(false); | ||||
|         $method->isStatic()->willReturn(false); | ||||
|         $method->returnsReference()->willReturn(false); | ||||
|         $method->getParameters()->willReturn(array($param1, $param2)); | ||||
|  | ||||
|         $param1->getName()->willReturn('arg_1'); | ||||
|         $param1->isArray()->willReturn(false); | ||||
|         if (version_compare(PHP_VERSION, '5.4', '>=')) { | ||||
|             $param1->isCallable()->willReturn(false); | ||||
|         } | ||||
|         $param1->getClass()->willReturn(null); | ||||
|         $param1->isDefaultValueAvailable()->willReturn(false); | ||||
|         $param1->isOptional()->willReturn(true); | ||||
|         $param1->isPassedByReference()->willReturn(true); | ||||
|         $param1->allowsNull()->willReturn(false); | ||||
|         if (defined('HHVM_VERSION')) { | ||||
|             $param1->getTypehintText()->willReturn(null); | ||||
|         } | ||||
|  | ||||
|         $param2->getName()->willReturn('arg2'); | ||||
|         $param2->isArray()->willReturn(false); | ||||
|         $param2->getClass()->willReturn($typeHint); | ||||
|         $param2->isDefaultValueAvailable()->willReturn(false); | ||||
|         $param2->isOptional()->willReturn(false); | ||||
|         $param2->isPassedByReference()->willReturn(false); | ||||
|         $param2->allowsNull()->willReturn(false); | ||||
|         $typeHint->getName()->willReturn('ArrayAccess'); | ||||
|  | ||||
|         $classNode   = $this->reflect($class, array()); | ||||
|         $methodNodes = $classNode->getMethods(); | ||||
|         $argNodes    = $methodNodes['methodWithArgs']->getArguments(); | ||||
|  | ||||
|         $argNodes[0]->isPassedByReference()->shouldReturn(true); | ||||
|         $argNodes[1]->isPassedByReference()->shouldReturn(false); | ||||
|     } | ||||
|  | ||||
|     /** | ||||
|      * @param ReflectionClass $class | ||||
|      */ | ||||
|     function it_throws_an_exception_if_class_is_final($class) | ||||
|     { | ||||
|         $class->isInterface()->willReturn(false); | ||||
|         $class->isFinal()->willReturn(true); | ||||
|         $class->getName()->willReturn('Custom\ClassName'); | ||||
|  | ||||
|         $this->shouldThrow('Prophecy\Exception\Doubler\ClassMirrorException') | ||||
|              ->duringReflect($class, array()); | ||||
|     } | ||||
|  | ||||
|     /** | ||||
|      * @param ReflectionClass  $class | ||||
|      * @param ReflectionMethod $method | ||||
|      */ | ||||
|     function it_ignores_final_methods($class, $method) | ||||
|     { | ||||
|         $class->getName()->willReturn('Custom\ClassName'); | ||||
|         $class->isInterface()->willReturn(false); | ||||
|         $class->isFinal()->willReturn(false); | ||||
|         $class->getMethods(ReflectionMethod::IS_ABSTRACT)->willReturn(array()); | ||||
|         $class->getMethods(ReflectionMethod::IS_PUBLIC)->willReturn(array($method)); | ||||
|  | ||||
|         $method->isFinal()->willReturn(true); | ||||
|         $method->getName()->willReturn('finalImplementation'); | ||||
|  | ||||
|         $classNode = $this->reflect($class, array()); | ||||
|         $classNode->getMethods()->shouldHaveCount(0); | ||||
|     } | ||||
|  | ||||
|     /** | ||||
|      * @param ReflectionClass $interface | ||||
|      */ | ||||
|     function it_throws_an_exception_if_interface_provided_instead_of_class($interface) | ||||
|     { | ||||
|         $interface->isInterface()->willReturn(true); | ||||
|         $interface->getName()->willReturn('Custom\ClassName'); | ||||
|  | ||||
|         $this->shouldThrow('Prophecy\Exception\InvalidArgumentException') | ||||
|              ->duringReflect($interface, array()); | ||||
|     } | ||||
|  | ||||
|     /** | ||||
|      * @param ReflectionClass  $interface1 | ||||
|      * @param ReflectionClass  $interface2 | ||||
|      * @param ReflectionMethod $method1 | ||||
|      * @param ReflectionMethod $method2 | ||||
|      * @param ReflectionMethod $method3 | ||||
|      */ | ||||
|     function it_reflects_all_interfaces_methods( | ||||
|         $interface1, $interface2, $method1, $method2, $method3 | ||||
|     ) | ||||
|     { | ||||
|         $interface1->getName()->willReturn('MyInterface1'); | ||||
|         $interface2->getName()->willReturn('MyInterface2'); | ||||
|  | ||||
|         $interface1->isInterface()->willReturn(true); | ||||
|         $interface2->isInterface()->willReturn(true); | ||||
|  | ||||
|         $interface1->getMethods()->willReturn(array($method1)); | ||||
|         $interface2->getMethods()->willReturn(array($method2, $method3)); | ||||
|  | ||||
|         $method1->getName()->willReturn('getName'); | ||||
|         $method2->getName()->willReturn('isPublic'); | ||||
|         $method3->getName()->willReturn('isAbstract'); | ||||
|  | ||||
|         $method1->isProtected()->willReturn(false); | ||||
|         $method2->isProtected()->willReturn(false); | ||||
|         $method3->isProtected()->willReturn(false); | ||||
|  | ||||
|         $method1->returnsReference()->willReturn(false); | ||||
|         $method2->returnsReference()->willReturn(false); | ||||
|         $method3->returnsReference()->willReturn(false); | ||||
|  | ||||
|         $method1->isStatic()->willReturn(false); | ||||
|         $method2->isStatic()->willReturn(false); | ||||
|         $method3->isStatic()->willReturn(false); | ||||
|  | ||||
|         $method1->getParameters()->willReturn(array()); | ||||
|         $method2->getParameters()->willReturn(array()); | ||||
|         $method3->getParameters()->willReturn(array()); | ||||
|  | ||||
|         $classNode = $this->reflect(null, array($interface1, $interface2)); | ||||
|  | ||||
|         $classNode->shouldBeAnInstanceOf('Prophecy\Doubler\Generator\Node\ClassNode'); | ||||
|         $classNode->getParentClass()->shouldReturn('stdClass'); | ||||
|         $classNode->getInterfaces()->shouldReturn(array( | ||||
|             'Prophecy\Doubler\Generator\ReflectionInterface', 'MyInterface2', 'MyInterface1', | ||||
|         )); | ||||
|  | ||||
|         $methodNodes = $classNode->getMethods(); | ||||
|         $methodNodes->shouldHaveCount(3); | ||||
|  | ||||
|         $classNode->hasMethod('getName')->shouldReturn(true); | ||||
|         $classNode->hasMethod('isPublic')->shouldReturn(true); | ||||
|         $classNode->hasMethod('isAbstract')->shouldReturn(true); | ||||
|     } | ||||
|  | ||||
|     /** | ||||
|      * @param ReflectionClass  $class | ||||
|      * @param ReflectionMethod $method1 | ||||
|      * @param ReflectionMethod $method2 | ||||
|      * @param ReflectionMethod $method3 | ||||
|      */ | ||||
|     function it_ignores_virtually_private_methods($class, $method1, $method2, $method3) | ||||
|     { | ||||
|         $class->getName()->willReturn('SomeClass'); | ||||
|         $class->isInterface()->willReturn(false); | ||||
|         $class->isFinal()->willReturn(false); | ||||
|         $class->getMethods(ReflectionMethod::IS_ABSTRACT)->willReturn(array()); | ||||
|         $class->getMethods(ReflectionMethod::IS_PUBLIC)->willReturn(array($method1, $method2, $method3)); | ||||
|  | ||||
|         $method1->getName()->willReturn('_getName'); | ||||
|         $method2->getName()->willReturn('__toString'); | ||||
|         $method3->getName()->willReturn('isAbstract'); | ||||
|  | ||||
|         $method1->isFinal()->willReturn(false); | ||||
|         $method2->isFinal()->willReturn(false); | ||||
|         $method3->isFinal()->willReturn(false); | ||||
|  | ||||
|         $method1->isProtected()->willReturn(false); | ||||
|         $method2->isProtected()->willReturn(false); | ||||
|         $method3->isProtected()->willReturn(false); | ||||
|  | ||||
|         $method1->isStatic()->willReturn(false); | ||||
|         $method2->isStatic()->willReturn(false); | ||||
|         $method3->isStatic()->willReturn(false); | ||||
|  | ||||
|         $method1->returnsReference()->willReturn(false); | ||||
|         $method2->returnsReference()->willReturn(false); | ||||
|         $method3->returnsReference()->willReturn(false); | ||||
|  | ||||
|         $method1->getParameters()->willReturn(array()); | ||||
|         $method2->getParameters()->willReturn(array()); | ||||
|         $method3->getParameters()->willReturn(array()); | ||||
|  | ||||
|         $classNode = $this->reflect($class, array()); | ||||
|         $methodNodes = $classNode->getMethods(); | ||||
|         $methodNodes->shouldHaveCount(2); | ||||
|  | ||||
|         $classNode->hasMethod('isAbstract')->shouldReturn(true); | ||||
|     } | ||||
|  | ||||
|     /** | ||||
|      * @param ReflectionClass  $class | ||||
|      * @param ReflectionMethod $method | ||||
|      */ | ||||
|     function it_does_not_throw_exception_for_virtually_private_finals($class, $method) | ||||
|     { | ||||
|         $class->getName()->willReturn('SomeClass'); | ||||
|         $class->isInterface()->willReturn(false); | ||||
|         $class->isFinal()->willReturn(false); | ||||
|         $class->getMethods(ReflectionMethod::IS_ABSTRACT)->willReturn(array()); | ||||
|         $class->getMethods(ReflectionMethod::IS_PUBLIC)->willReturn(array($method)); | ||||
|  | ||||
|         $method->getName()->willReturn('__toString'); | ||||
|         $method->isFinal()->willReturn(true); | ||||
|  | ||||
|         $this->shouldNotThrow()->duringReflect($class, array()); | ||||
|     } | ||||
|  | ||||
|     /** | ||||
|      * @param ReflectionClass $class | ||||
|      */ | ||||
|     function it_throws_an_exception_if_class_provided_in_interfaces_list($class) | ||||
|     { | ||||
|         $class->getName()->willReturn('MyClass'); | ||||
|         $class->isInterface()->willReturn(false); | ||||
|  | ||||
|         $this->shouldThrow('InvalidArgumentException') | ||||
|              ->duringReflect(null, array($class)); | ||||
|     } | ||||
|  | ||||
|     function it_throws_an_exception_if_not_reflection_provided_as_interface() | ||||
|     { | ||||
|         $this->shouldThrow('InvalidArgumentException') | ||||
|              ->duringReflect(null, array(null)); | ||||
|     } | ||||
|  | ||||
|     function it_doesnt_fail_to_typehint_nonexistent_FQCN() | ||||
|     { | ||||
|         $classNode = $this->reflect(new ReflectionClass('spec\Prophecy\Doubler\Generator\OptionalDepsClass'), array()); | ||||
|         $method = $classNode->getMethod('iHaveAStrangeTypeHintedArg'); | ||||
|         $arguments = $method->getArguments(); | ||||
|         $arguments[0]->getTypeHint()->shouldBe('I\Simply\Am\Nonexistent'); | ||||
|     } | ||||
|  | ||||
|     function it_doesnt_fail_to_typehint_nonexistent_RQCN() | ||||
|     { | ||||
|         $classNode = $this->reflect(new ReflectionClass('spec\Prophecy\Doubler\Generator\OptionalDepsClass'), array()); | ||||
|         $method = $classNode->getMethod('iHaveAnEvenStrangerTypeHintedArg'); | ||||
|         $arguments = $method->getArguments(); | ||||
|         $arguments[0]->getTypeHint()->shouldBe('I\Simply\Am\Not'); | ||||
|     } | ||||
|  | ||||
|     function it_doesnt_use_scalar_typehints() | ||||
|     { | ||||
|         $classNode = $this->reflect(new ReflectionClass('ReflectionMethod'), array()); | ||||
|         $method = $classNode->getMethod('export'); | ||||
|         $arguments = $method->getArguments(); | ||||
|         $arguments[0]->getTypeHint()->shouldReturn(null); | ||||
|         $arguments[1]->getTypeHint()->shouldReturn(null); | ||||
|         $arguments[2]->getTypeHint()->shouldReturn(null); | ||||
|     } | ||||
| } | ||||
|  | ||||
| class OptionalDepsClass | ||||
| { | ||||
|     public function iHaveAStrangeTypeHintedArg(\I\Simply\Am\Nonexistent $class) | ||||
|     { | ||||
|     } | ||||
|  | ||||
|     public function iHaveAnEvenStrangerTypeHintedArg(Simply\Am\Not $class) | ||||
|     { | ||||
|     } | ||||
| } | ||||
| @@ -1,62 +0,0 @@ | ||||
| <?php | ||||
|  | ||||
| namespace spec\Prophecy\Doubler\Generator\Node; | ||||
|  | ||||
| use PhpSpec\ObjectBehavior; | ||||
|  | ||||
| class ArgumentNodeSpec extends ObjectBehavior | ||||
| { | ||||
|     function let() | ||||
|     { | ||||
|         $this->beConstructedWith('name'); | ||||
|     } | ||||
|  | ||||
|     function it_is_not_be_passed_by_reference_by_default() | ||||
|     { | ||||
|         $this->shouldNotBePassedByReference(); | ||||
|     } | ||||
|  | ||||
|     function it_is_passed_by_reference_if_marked() | ||||
|     { | ||||
|         $this->setAsPassedByReference(); | ||||
|         $this->shouldBePassedByReference(); | ||||
|     } | ||||
|  | ||||
|     function it_has_name_with_which_it_was_been_constructed() | ||||
|     { | ||||
|         $this->getName()->shouldReturn('name'); | ||||
|     } | ||||
|  | ||||
|     function it_has_no_typehint_by_default() | ||||
|     { | ||||
|         $this->getTypeHint()->shouldReturn(null); | ||||
|     } | ||||
|  | ||||
|     function its_typeHint_is_mutable() | ||||
|     { | ||||
|         $this->setTypeHint('array'); | ||||
|         $this->getTypeHint()->shouldReturn('array'); | ||||
|     } | ||||
|  | ||||
|     function it_does_not_have_default_value_by_default() | ||||
|     { | ||||
|         $this->getDefault()->shouldReturn(null); | ||||
|     } | ||||
|  | ||||
|     function it_is_not_optional_by_default() | ||||
|     { | ||||
|         $this->isOptional()->shouldReturn(false); | ||||
|     } | ||||
|  | ||||
|     function its_default_is_mutable() | ||||
|     { | ||||
|         $this->setDefault(array()); | ||||
|         $this->getDefault()->shouldReturn(array()); | ||||
|     } | ||||
|  | ||||
|     function it_is_marked_as_optional_when_default_is_set() | ||||
|     { | ||||
|         $this->setDefault(null); | ||||
|         $this->isOptional()->shouldReturn(true); | ||||
|     } | ||||
| } | ||||
| @@ -1,154 +0,0 @@ | ||||
| <?php | ||||
|  | ||||
| namespace spec\Prophecy\Doubler\Generator\Node; | ||||
|  | ||||
| use PhpSpec\ObjectBehavior; | ||||
|  | ||||
| class ClassNodeSpec extends ObjectBehavior | ||||
| { | ||||
|     function its_parentClass_is_a_stdClass_by_default() | ||||
|     { | ||||
|         $this->getParentClass()->shouldReturn('stdClass'); | ||||
|     } | ||||
|  | ||||
|     function its_parentClass_is_mutable() | ||||
|     { | ||||
|         $this->setParentClass('Exception'); | ||||
|         $this->getParentClass()->shouldReturn('Exception'); | ||||
|     } | ||||
|  | ||||
|     function its_parentClass_is_set_to_stdClass_if_user_set_null() | ||||
|     { | ||||
|         $this->setParentClass(null); | ||||
|         $this->getParentClass()->shouldReturn('stdClass'); | ||||
|     } | ||||
|  | ||||
|     function it_does_not_implement_any_interface_by_default() | ||||
|     { | ||||
|         $this->getInterfaces()->shouldHaveCount(0); | ||||
|     } | ||||
|  | ||||
|     function its_addInterface_adds_item_to_the_list_of_implemented_interfaces() | ||||
|     { | ||||
|         $this->addInterface('MyInterface'); | ||||
|         $this->getInterfaces()->shouldHaveCount(1); | ||||
|     } | ||||
|  | ||||
|     function its_hasInterface_returns_true_if_class_implements_interface() | ||||
|     { | ||||
|         $this->addInterface('MyInterface'); | ||||
|         $this->hasInterface('MyInterface')->shouldReturn(true); | ||||
|     } | ||||
|  | ||||
|     function its_hasInterface_returns_false_if_class_does_not_implements_interface() | ||||
|     { | ||||
|         $this->hasInterface('MyInterface')->shouldReturn(false); | ||||
|     } | ||||
|  | ||||
|     function it_supports_implementation_of_multiple_interfaces() | ||||
|     { | ||||
|         $this->addInterface('MyInterface'); | ||||
|         $this->addInterface('MySecondInterface'); | ||||
|         $this->getInterfaces()->shouldHaveCount(2); | ||||
|     } | ||||
|  | ||||
|     function it_ignores_same_interfaces_added_twice() | ||||
|     { | ||||
|         $this->addInterface('MyInterface'); | ||||
|         $this->addInterface('MyInterface'); | ||||
|  | ||||
|         $this->getInterfaces()->shouldHaveCount(1); | ||||
|         $this->getInterfaces()->shouldReturn(array('MyInterface')); | ||||
|     } | ||||
|  | ||||
|     function it_does_not_have_methods_by_default() | ||||
|     { | ||||
|         $this->getMethods()->shouldHaveCount(0); | ||||
|     } | ||||
|  | ||||
|     /** | ||||
|      * @param \Prophecy\Doubler\Generator\Node\MethodNode $method1 | ||||
|      * @param \Prophecy\Doubler\Generator\Node\MethodNode $method2 | ||||
|      */ | ||||
|     function it_can_has_methods($method1, $method2) | ||||
|     { | ||||
|         $method1->getName()->willReturn('__construct'); | ||||
|         $method2->getName()->willReturn('getName'); | ||||
|  | ||||
|         $this->addMethod($method1); | ||||
|         $this->addMethod($method2); | ||||
|  | ||||
|         $this->getMethods()->shouldReturn(array( | ||||
|             '__construct' => $method1, | ||||
|             'getName'     => $method2 | ||||
|         )); | ||||
|     } | ||||
|  | ||||
|     /** | ||||
|      * @param \Prophecy\Doubler\Generator\Node\MethodNode $method | ||||
|      */ | ||||
|     function its_hasMethod_returns_true_if_method_exists($method) | ||||
|     { | ||||
|         $method->getName()->willReturn('getName'); | ||||
|  | ||||
|         $this->addMethod($method); | ||||
|  | ||||
|         $this->hasMethod('getName')->shouldReturn(true); | ||||
|     } | ||||
|  | ||||
|     /** | ||||
|      * @param \Prophecy\Doubler\Generator\Node\MethodNode $method | ||||
|      */ | ||||
|     function its_getMethod_returns_method_by_name($method) | ||||
|     { | ||||
|         $method->getName()->willReturn('getName'); | ||||
|  | ||||
|         $this->addMethod($method); | ||||
|  | ||||
|         $this->getMethod('getName')->shouldReturn($method); | ||||
|     } | ||||
|  | ||||
|     function its_hasMethod_returns_false_if_method_does_not_exists() | ||||
|     { | ||||
|         $this->hasMethod('getName')->shouldReturn(false); | ||||
|     } | ||||
|  | ||||
|     /** | ||||
|      * @param \Prophecy\Doubler\Generator\Node\MethodNode $method | ||||
|      */ | ||||
|     function its_hasMethod_returns_false_if_method_has_been_removed($method) | ||||
|     { | ||||
|         $method->getName()->willReturn('getName'); | ||||
|         $this->addMethod($method); | ||||
|         $this->removeMethod('getName'); | ||||
|  | ||||
|         $this->hasMethod('getName')->shouldReturn(false); | ||||
|     } | ||||
|  | ||||
|  | ||||
|     function it_does_not_have_properties_by_default() | ||||
|     { | ||||
|         $this->getProperties()->shouldHaveCount(0); | ||||
|     } | ||||
|  | ||||
|     function it_is_able_to_have_properties() | ||||
|     { | ||||
|         $this->addProperty('title'); | ||||
|         $this->addProperty('text', 'private'); | ||||
|         $this->getProperties()->shouldReturn(array( | ||||
|             'title' => 'public', | ||||
|             'text'  => 'private' | ||||
|         )); | ||||
|     } | ||||
|  | ||||
|     function its_addProperty_does_not_accept_unsupported_visibility() | ||||
|     { | ||||
|         $this->shouldThrow('InvalidArgumentException')->duringAddProperty('title', 'town'); | ||||
|     } | ||||
|  | ||||
|     function its_addProperty_lowercases_visibility_before_setting() | ||||
|     { | ||||
|         $this->addProperty('text', 'PRIVATE'); | ||||
|         $this->getProperties()->shouldReturn(array('text' => 'private')); | ||||
|     } | ||||
| } | ||||
| @@ -1,123 +0,0 @@ | ||||
| <?php | ||||
|  | ||||
| namespace spec\Prophecy\Doubler\Generator\Node; | ||||
|  | ||||
| use PhpSpec\ObjectBehavior; | ||||
|  | ||||
| class MethodNodeSpec extends ObjectBehavior | ||||
| { | ||||
|     function let() | ||||
|     { | ||||
|         $this->beConstructedWith('getTitle'); | ||||
|     } | ||||
|  | ||||
|     function it_has_a_name() | ||||
|     { | ||||
|         $this->getName()->shouldReturn('getTitle'); | ||||
|     } | ||||
|  | ||||
|     function it_has_public_visibility_by_default() | ||||
|     { | ||||
|         $this->getVisibility()->shouldReturn('public'); | ||||
|     } | ||||
|  | ||||
|     function its_visibility_is_mutable() | ||||
|     { | ||||
|         $this->setVisibility('private'); | ||||
|         $this->getVisibility()->shouldReturn('private'); | ||||
|     } | ||||
|  | ||||
|     function it_is_not_static_by_default() | ||||
|     { | ||||
|         $this->shouldNotBeStatic(); | ||||
|     } | ||||
|  | ||||
|     function it_does_not_return_a_reference_by_default() | ||||
|     { | ||||
|         $this->returnsReference()->shouldReturn(false); | ||||
|     } | ||||
|  | ||||
|     function it_should_be_settable_as_returning_a_reference_through_setter() | ||||
|     { | ||||
|         $this->setReturnsReference(); | ||||
|         $this->returnsReference()->shouldReturn(true); | ||||
|     }  | ||||
|  | ||||
|     function it_should_be_settable_as_static_through_setter() | ||||
|     { | ||||
|         $this->setStatic(); | ||||
|         $this->shouldBeStatic(); | ||||
|     } | ||||
|  | ||||
|     function it_accepts_only_supported_visibilities() | ||||
|     { | ||||
|         $this->shouldThrow('InvalidArgumentException')->duringSetVisibility('stealth'); | ||||
|     } | ||||
|  | ||||
|     function it_lowercases_visibility_before_setting_it() | ||||
|     { | ||||
|         $this->setVisibility('Public'); | ||||
|         $this->getVisibility()->shouldReturn('public'); | ||||
|     } | ||||
|  | ||||
|     /** | ||||
|      * @param \Prophecy\Doubler\Generator\Node\ArgumentNode $argument1 | ||||
|      * @param \Prophecy\Doubler\Generator\Node\ArgumentNode $argument2 | ||||
|      */ | ||||
|     function its_useParentCode_causes_method_to_call_parent($argument1, $argument2) | ||||
|     { | ||||
|         $argument1->getName()->willReturn('objectName'); | ||||
|         $argument2->getName()->willReturn('default'); | ||||
|  | ||||
|         $this->addArgument($argument1); | ||||
|         $this->addArgument($argument2); | ||||
|  | ||||
|         $this->useParentCode(); | ||||
|  | ||||
|         $this->getCode()->shouldReturn( | ||||
|             'return parent::getTitle($objectName, $default);' | ||||
|         ); | ||||
|     } | ||||
|  | ||||
|     function its_code_is_mutable() | ||||
|     { | ||||
|         $this->setCode('echo "code";'); | ||||
|         $this->getCode()->shouldReturn('echo "code";'); | ||||
|     } | ||||
|  | ||||
|     function its_reference_returning_methods_will_generate_exceptions() | ||||
|     { | ||||
|         $this->setCode('echo "code";'); | ||||
|         $this->setReturnsReference(); | ||||
|         $this->getCode()->shouldReturn("throw new \Prophecy\Exception\Doubler\ReturnByReferenceException('Returning by reference not supported', get_class(\$this), 'getTitle');"); | ||||
|     } | ||||
|  | ||||
|     function its_setCode_provided_with_null_cleans_method_body() | ||||
|     { | ||||
|         $this->setCode(null); | ||||
|         $this->getCode()->shouldReturn(''); | ||||
|     } | ||||
|  | ||||
|     function it_is_constructable_with_code() | ||||
|     { | ||||
|         $this->beConstructedWith('getTitle', 'die();'); | ||||
|         $this->getCode()->shouldReturn('die();'); | ||||
|     } | ||||
|  | ||||
|     function it_does_not_have_arguments_by_default() | ||||
|     { | ||||
|         $this->getArguments()->shouldHaveCount(0); | ||||
|     } | ||||
|  | ||||
|     /** | ||||
|      * @param \Prophecy\Doubler\Generator\Node\ArgumentNode $argument1 | ||||
|      * @param \Prophecy\Doubler\Generator\Node\ArgumentNode $argument2 | ||||
|      */ | ||||
|     function it_supports_adding_arguments($argument1, $argument2) | ||||
|     { | ||||
|         $this->addArgument($argument1); | ||||
|         $this->addArgument($argument2); | ||||
|  | ||||
|         $this->getArguments()->shouldReturn(array($argument1, $argument2)); | ||||
|     } | ||||
| } | ||||
| @@ -1,96 +0,0 @@ | ||||
| <?php | ||||
|  | ||||
| namespace spec\Prophecy\Doubler; | ||||
|  | ||||
| use PhpSpec\ObjectBehavior; | ||||
|  | ||||
| class LazyDoubleSpec extends ObjectBehavior | ||||
| { | ||||
|     /** | ||||
|      * @param \Prophecy\Doubler\Doubler $doubler | ||||
|      */ | ||||
|     function let($doubler) | ||||
|     { | ||||
|         $this->beConstructedWith($doubler); | ||||
|     } | ||||
|  | ||||
|     /** | ||||
|      * @param \Prophecy\Prophecy\ProphecySubjectInterface $double | ||||
|      */ | ||||
|     function it_returns_anonymous_double_instance_by_default($doubler, $double) | ||||
|     { | ||||
|         $doubler->double(null, array())->willReturn($double); | ||||
|  | ||||
|         $this->getInstance()->shouldReturn($double); | ||||
|     } | ||||
|  | ||||
|     /** | ||||
|      * @param \Prophecy\Prophecy\ProphecySubjectInterface $double | ||||
|      * @param \ReflectionClass                            $class | ||||
|      */ | ||||
|     function it_returns_class_double_instance_if_set($doubler, $double, $class) | ||||
|     { | ||||
|         $doubler->double($class, array())->willReturn($double); | ||||
|  | ||||
|         $this->setParentClass($class); | ||||
|  | ||||
|         $this->getInstance()->shouldReturn($double); | ||||
|     } | ||||
|  | ||||
|     /** | ||||
|      * @param \Prophecy\Prophecy\ProphecySubjectInterface $double1 | ||||
|      * @param \Prophecy\Prophecy\ProphecySubjectInterface $double2 | ||||
|      */ | ||||
|     function it_returns_same_double_instance_if_called_2_times( | ||||
|         $doubler, $double1, $double2 | ||||
|     ) | ||||
|     { | ||||
|         $doubler->double(null, array())->willReturn($double1); | ||||
|         $doubler->double(null, array())->willReturn($double2); | ||||
|  | ||||
|         $this->getInstance()->shouldReturn($double2); | ||||
|         $this->getInstance()->shouldReturn($double2); | ||||
|     } | ||||
|  | ||||
|     function its_setParentClass_throws_ClassNotFoundException_if_class_not_found() | ||||
|     { | ||||
|         $this->shouldThrow('Prophecy\Exception\Doubler\ClassNotFoundException') | ||||
|             ->duringSetParentClass('SomeUnexistingClass'); | ||||
|     } | ||||
|  | ||||
|     /** | ||||
|      * @param \Prophecy\Prophecy\ProphecySubjectInterface $double | ||||
|      */ | ||||
|     function its_setParentClass_throws_exception_if_prophecy_is_already_created( | ||||
|         $doubler, $double | ||||
|     ) | ||||
|     { | ||||
|         $doubler->double(null, array())->willReturn($double); | ||||
|  | ||||
|         $this->getInstance(); | ||||
|  | ||||
|         $this->shouldThrow('Prophecy\Exception\Doubler\DoubleException') | ||||
|             ->duringSetParentClass('stdClass'); | ||||
|     } | ||||
|  | ||||
|     function its_addInterface_throws_InterfaceNotFoundException_if_no_interface_found() | ||||
|     { | ||||
|         $this->shouldThrow('Prophecy\Exception\Doubler\InterfaceNotFoundException') | ||||
|             ->duringAddInterface('SomeUnexistingInterface'); | ||||
|     } | ||||
|  | ||||
|     /** | ||||
|      * @param \Prophecy\Prophecy\ProphecySubjectInterface $double | ||||
|      */ | ||||
|     function its_addInterface_throws_exception_if_prophecy_is_already_created( | ||||
|         $doubler, $double | ||||
|     ) | ||||
|     { | ||||
|         $doubler->double(null, array())->willReturn($double); | ||||
|  | ||||
|         $this->getInstance(); | ||||
|  | ||||
|         $this->shouldThrow('Prophecy\Exception\Doubler\DoubleException') | ||||
|             ->duringAddInterface('ArrayAccess'); | ||||
|     } | ||||
| } | ||||
| @@ -1,72 +0,0 @@ | ||||
| <?php | ||||
|  | ||||
| namespace spec\Prophecy\Doubler; | ||||
|  | ||||
| use PhpSpec\ObjectBehavior; | ||||
|  | ||||
| class NameGeneratorSpec extends ObjectBehavior | ||||
| { | ||||
|     /** | ||||
|      * @param \ReflectionClass $class | ||||
|      */ | ||||
|     function its_name_generates_name_based_on_simple_class_reflection($class) | ||||
|     { | ||||
|         $class->getName()->willReturn('stdClass'); | ||||
|         $this->name($class, array())->shouldStartWith('Double\stdClass\\'); | ||||
|     } | ||||
|  | ||||
|     /** | ||||
|      * @param \ReflectionClass $class | ||||
|      */ | ||||
|     function its_name_generates_name_based_on_namespaced_class_reflection($class) | ||||
|     { | ||||
|         $class->getName()->willReturn('Some\Custom\Class'); | ||||
|         $this->name($class, array())->shouldStartWith('Double\Some\Custom\Class\P'); | ||||
|     } | ||||
|  | ||||
|     /** | ||||
|      * @param \ReflectionClass $interface1 | ||||
|      * @param \ReflectionClass $interface2 | ||||
|      */ | ||||
|     function its_name_generates_name_based_on_interface_shortnames($interface1, $interface2) | ||||
|     { | ||||
|         $interface1->getShortName()->willReturn('HandlerInterface'); | ||||
|         $interface2->getShortName()->willReturn('LoaderInterface'); | ||||
|  | ||||
|         $this->name(null, array($interface1, $interface2))->shouldStartWith( | ||||
|             'Double\HandlerInterface\LoaderInterface\P' | ||||
|         ); | ||||
|     } | ||||
|  | ||||
|     function it_generates_proper_name_for_no_class_and_interfaces_list() | ||||
|     { | ||||
|         $this->name(null, array())->shouldStartWith('Double\stdClass\P'); | ||||
|     } | ||||
|  | ||||
|     /** | ||||
|      * @param \ReflectionClass $class | ||||
|      * @param \ReflectionClass $interface1 | ||||
|      * @param \ReflectionClass $interface2 | ||||
|      */ | ||||
|     function its_name_generates_name_based_only_on_class_if_its_available( | ||||
|         $class, $interface1, $interface2 | ||||
|     ) | ||||
|     { | ||||
|         $class->getName()->willReturn('Some\Custom\Class'); | ||||
|         $interface1->getShortName()->willReturn('HandlerInterface'); | ||||
|         $interface2->getShortName()->willReturn('LoaderInterface'); | ||||
|  | ||||
|         $this->name($class, array($interface1, $interface2))->shouldStartWith( | ||||
|             'Double\Some\Custom\Class\P' | ||||
|         ); | ||||
|     } | ||||
|  | ||||
|     public function getMatchers() | ||||
|     { | ||||
|         return array( | ||||
|             'startWith' => function ($subject, $string) { | ||||
|                 return 0 === strpos($subject, $string); | ||||
|             }, | ||||
|         ); | ||||
|     } | ||||
| } | ||||
| @@ -1,32 +0,0 @@ | ||||
| <?php | ||||
|  | ||||
| namespace spec\Prophecy\Exception\Call; | ||||
|  | ||||
| use PhpSpec\ObjectBehavior; | ||||
| use spec\Prophecy\Exception\Prophecy\Prophecy; | ||||
|  | ||||
| class UnexpectedCallExceptionSpec extends ObjectBehavior | ||||
| { | ||||
|     /** | ||||
|      * @param \Prophecy\Prophecy\ObjectProphecy $objectProphecy | ||||
|      */ | ||||
|     function let($objectProphecy) | ||||
|     { | ||||
|         $this->beConstructedWith('msg', $objectProphecy, 'getName', array('arg1', 'arg2')); | ||||
|     } | ||||
|  | ||||
|     function it_is_prophecy_exception() | ||||
|     { | ||||
|         $this->shouldBeAnInstanceOf('Prophecy\Exception\Prophecy\ObjectProphecyException'); | ||||
|     } | ||||
|  | ||||
|     function it_exposes_method_name_through_getter() | ||||
|     { | ||||
|         $this->getMethodName()->shouldReturn('getName'); | ||||
|     } | ||||
|  | ||||
|     function it_exposes_arguments_through_getter() | ||||
|     { | ||||
|         $this->getArguments()->shouldReturn(array('arg1', 'arg2')); | ||||
|     } | ||||
| } | ||||
| @@ -1,28 +0,0 @@ | ||||
| <?php | ||||
|  | ||||
| namespace spec\Prophecy\Exception\Doubler; | ||||
|  | ||||
| use PhpSpec\ObjectBehavior; | ||||
| use spec\Prophecy\Exception\Prophecy; | ||||
|  | ||||
| class ClassCreatorExceptionSpec extends ObjectBehavior | ||||
| { | ||||
|     /** | ||||
|      * @param \Prophecy\Doubler\Generator\Node\ClassNode $node | ||||
|      */ | ||||
|     function let($node) | ||||
|     { | ||||
|         $this->beConstructedWith('', $node); | ||||
|     } | ||||
|  | ||||
|     function it_is_a_prophecy_exception() | ||||
|     { | ||||
|         $this->shouldBeAnInstanceOf('Prophecy\Exception\Exception'); | ||||
|         $this->shouldBeAnInstanceOf('Prophecy\Exception\Doubler\DoublerException'); | ||||
|     } | ||||
|  | ||||
|     function it_contains_a_reflected_node($node) | ||||
|     { | ||||
|         $this->getClassNode()->shouldReturn($node); | ||||
|     } | ||||
| } | ||||
| @@ -1,27 +0,0 @@ | ||||
| <?php | ||||
|  | ||||
| namespace spec\Prophecy\Exception\Doubler; | ||||
|  | ||||
| use PhpSpec\ObjectBehavior; | ||||
|  | ||||
| class ClassMirrorExceptionSpec extends ObjectBehavior | ||||
| { | ||||
|     /** | ||||
|      * @param \ReflectionClass $class | ||||
|      */ | ||||
|     function let($class) | ||||
|     { | ||||
|         $this->beConstructedWith('', $class); | ||||
|     } | ||||
|  | ||||
|     function it_is_a_prophecy_exception() | ||||
|     { | ||||
|         $this->shouldBeAnInstanceOf('Prophecy\Exception\Exception'); | ||||
|         $this->shouldBeAnInstanceOf('Prophecy\Exception\Doubler\DoublerException'); | ||||
|     } | ||||
|  | ||||
|     function it_contains_a_reflected_class_link($class) | ||||
|     { | ||||
|         $this->getReflectedClass()->shouldReturn($class); | ||||
|     } | ||||
| } | ||||
| @@ -1,25 +0,0 @@ | ||||
| <?php | ||||
|  | ||||
| namespace spec\Prophecy\Exception\Doubler; | ||||
|  | ||||
| use PhpSpec\ObjectBehavior; | ||||
| use spec\Prophecy\Exception\Prophecy; | ||||
|  | ||||
| class ClassNotFoundExceptionSpec extends ObjectBehavior | ||||
| { | ||||
|     function let() | ||||
|     { | ||||
|         $this->beConstructedWith('msg', 'CustomClass'); | ||||
|     } | ||||
|  | ||||
|     function it_is_a_prophecy_exception() | ||||
|     { | ||||
|         $this->shouldBeAnInstanceOf('Prophecy\Exception\Exception'); | ||||
|         $this->shouldBeAnInstanceOf('Prophecy\Exception\Doubler\DoubleException'); | ||||
|     } | ||||
|  | ||||
|     function its_getClassname_returns_classname() | ||||
|     { | ||||
|         $this->getClassname()->shouldReturn('CustomClass'); | ||||
|     } | ||||
| } | ||||
| @@ -1,14 +0,0 @@ | ||||
| <?php | ||||
|  | ||||
| namespace spec\Prophecy\Exception\Doubler; | ||||
|  | ||||
| use PhpSpec\ObjectBehavior; | ||||
|  | ||||
| class DoubleExceptionSpec extends ObjectBehavior | ||||
| { | ||||
|     function it_is_a_double_exception() | ||||
|     { | ||||
|         $this->shouldBeAnInstanceOf('RuntimeException'); | ||||
|         $this->shouldBeAnInstanceOf('Prophecy\Exception\Doubler\DoublerException'); | ||||
|     } | ||||
| } | ||||
| @@ -1,24 +0,0 @@ | ||||
| <?php | ||||
|  | ||||
| namespace spec\Prophecy\Exception\Doubler; | ||||
|  | ||||
| use PhpSpec\ObjectBehavior; | ||||
| use spec\Prophecy\Exception\Prophecy; | ||||
|  | ||||
| class InterfaceNotFoundExceptionSpec extends ObjectBehavior | ||||
| { | ||||
|     function let() | ||||
|     { | ||||
|         $this->beConstructedWith('msg', 'CustomInterface'); | ||||
|     } | ||||
|  | ||||
|     function it_extends_ClassNotFoundException() | ||||
|     { | ||||
|         $this->shouldBeAnInstanceOf('Prophecy\Exception\Doubler\ClassNotFoundException'); | ||||
|     } | ||||
|  | ||||
|     function its_getClassname_returns_classname() | ||||
|     { | ||||
|         $this->getClassname()->shouldReturn('CustomInterface'); | ||||
|     } | ||||
| } | ||||
| @@ -1,40 +0,0 @@ | ||||
| <?php | ||||
|  | ||||
| namespace spec\Prophecy\Exception\Doubler; | ||||
|  | ||||
| use PhpSpec\ObjectBehavior; | ||||
| use spec\Prophecy\Exception\Prophecy; | ||||
|  | ||||
| class MethodNotFoundExceptionSpec extends ObjectBehavior | ||||
| { | ||||
|     function let() | ||||
|     { | ||||
|         $this->beConstructedWith('', 'User', 'getName', array(1, 2, 3)); | ||||
|     } | ||||
|  | ||||
|     function it_is_DoubleException() | ||||
|     { | ||||
|         $this->shouldHaveType('Prophecy\Exception\Doubler\DoubleException'); | ||||
|     } | ||||
|  | ||||
|     function it_has_MethodName() | ||||
|     { | ||||
|         $this->getMethodName()->shouldReturn('getName'); | ||||
|     } | ||||
|  | ||||
|     function it_has_classnamej() | ||||
|     { | ||||
|         $this->getClassname()->shouldReturn('User'); | ||||
|     } | ||||
|  | ||||
|     function it_has_an_arguments_list() | ||||
|     { | ||||
|         $this->getArguments()->shouldReturn(array(1, 2, 3)); | ||||
|     } | ||||
|  | ||||
|     function it_has_a_default_null_argument_list() | ||||
|     { | ||||
|         $this->beConstructedWith('', 'User', 'getName'); | ||||
|         $this->getArguments()->shouldReturn(null); | ||||
|     } | ||||
| } | ||||
| @@ -1,57 +0,0 @@ | ||||
| <?php | ||||
|  | ||||
| namespace spec\Prophecy\Exception\Prediction; | ||||
|  | ||||
| use PhpSpec\ObjectBehavior; | ||||
|  | ||||
| class AggregateExceptionSpec extends ObjectBehavior | ||||
| { | ||||
|     function let() | ||||
|     { | ||||
|         $this->beConstructedWith(null); | ||||
|     } | ||||
|  | ||||
|     function it_is_prediction_exception() | ||||
|     { | ||||
|         $this->shouldBeAnInstanceOf('RuntimeException'); | ||||
|         $this->shouldBeAnInstanceOf('Prophecy\Exception\Prediction\PredictionException'); | ||||
|     } | ||||
|  | ||||
|     /** | ||||
|      * @param \Prophecy\Prophecy\ObjectProphecy $object | ||||
|      */ | ||||
|     function it_can_store_objectProphecy_link($object) | ||||
|     { | ||||
|         $this->setObjectProphecy($object); | ||||
|         $this->getObjectProphecy()->shouldReturn($object); | ||||
|     } | ||||
|  | ||||
|     function it_should_not_have_exceptions_at_the_beginning() | ||||
|     { | ||||
|         $this->getExceptions()->shouldHaveCount(0); | ||||
|     } | ||||
|  | ||||
|     /** | ||||
|      * @param \Prophecy\Exception\Prediction\PredictionException $exception | ||||
|      */ | ||||
|     function it_should_append_exception_through_append_method($exception) | ||||
|     { | ||||
|         $exception->getMessage()->willReturn('Exception #1'); | ||||
|  | ||||
|         $this->append($exception); | ||||
|  | ||||
|         $this->getExceptions()->shouldReturn(array($exception)); | ||||
|     } | ||||
|  | ||||
|     /** | ||||
|      * @param \Prophecy\Exception\Prediction\PredictionException $exception | ||||
|      */ | ||||
|     function it_should_update_message_during_append($exception) | ||||
|     { | ||||
|         $exception->getMessage()->willReturn('Exception #1'); | ||||
|  | ||||
|         $this->append($exception); | ||||
|  | ||||
|         $this->getMessage()->shouldReturn("  Exception #1"); | ||||
|     } | ||||
| } | ||||
| @@ -1,29 +0,0 @@ | ||||
| <?php | ||||
|  | ||||
| namespace spec\Prophecy\Exception\Prediction; | ||||
|  | ||||
| use PhpSpec\ObjectBehavior; | ||||
|  | ||||
| class NoCallsExceptionSpec extends ObjectBehavior | ||||
| { | ||||
|     /** | ||||
|      * @param \Prophecy\Prophecy\ObjectProphecy $objectProphecy | ||||
|      * @param \Prophecy\Prophecy\MethodProphecy $methodProphecy | ||||
|      */ | ||||
|     function let($objectProphecy, $methodProphecy) | ||||
|     { | ||||
|         $methodProphecy->getObjectProphecy()->willReturn($objectProphecy); | ||||
|  | ||||
|         $this->beConstructedWith('message', $methodProphecy); | ||||
|     } | ||||
|  | ||||
|     function it_is_PredictionException() | ||||
|     { | ||||
|         $this->shouldHaveType('Prophecy\Exception\Prediction\PredictionException'); | ||||
|     } | ||||
|  | ||||
|     function it_extends_MethodProphecyException() | ||||
|     { | ||||
|         $this->shouldHaveType('Prophecy\Exception\Prophecy\MethodProphecyException'); | ||||
|     } | ||||
| } | ||||
| @@ -1,31 +0,0 @@ | ||||
| <?php | ||||
|  | ||||
| namespace spec\Prophecy\Exception\Prediction; | ||||
|  | ||||
| use PhpSpec\ObjectBehavior; | ||||
|  | ||||
| class UnexpectedCallsCountExceptionSpec extends ObjectBehavior | ||||
| { | ||||
|     /** | ||||
|      * @param \Prophecy\Prophecy\ObjectProphecy $objectProphecy | ||||
|      * @param \Prophecy\Prophecy\MethodProphecy $methodProphecy | ||||
|      * @param \Prophecy\Call\Call               $call1 | ||||
|      * @param \Prophecy\Call\Call               $call2 | ||||
|      */ | ||||
|     function let($objectProphecy, $methodProphecy, $call1, $call2) | ||||
|     { | ||||
|         $methodProphecy->getObjectProphecy()->willReturn($objectProphecy); | ||||
|  | ||||
|         $this->beConstructedWith('message', $methodProphecy, 5, array($call1, $call2)); | ||||
|     } | ||||
|  | ||||
|     function it_extends_UnexpectedCallsException() | ||||
|     { | ||||
|         $this->shouldBeAnInstanceOf('Prophecy\Exception\Prediction\UnexpectedCallsException'); | ||||
|     } | ||||
|  | ||||
|     function it_should_expose_expectedCount_through_getter() | ||||
|     { | ||||
|         $this->getExpectedCount()->shouldReturn(5); | ||||
|     } | ||||
| } | ||||
| @@ -1,36 +0,0 @@ | ||||
| <?php | ||||
|  | ||||
| namespace spec\Prophecy\Exception\Prediction; | ||||
|  | ||||
| use PhpSpec\ObjectBehavior; | ||||
|  | ||||
| class UnexpectedCallsExceptionSpec extends ObjectBehavior | ||||
| { | ||||
|     /** | ||||
|      * @param \Prophecy\Prophecy\ObjectProphecy $objectProphecy | ||||
|      * @param \Prophecy\Prophecy\MethodProphecy $methodProphecy | ||||
|      * @param \Prophecy\Call\Call               $call1 | ||||
|      * @param \Prophecy\Call\Call               $call2 | ||||
|      */ | ||||
|     function let($objectProphecy, $methodProphecy, $call1, $call2) | ||||
|     { | ||||
|         $methodProphecy->getObjectProphecy()->willReturn($objectProphecy); | ||||
|  | ||||
|         $this->beConstructedWith('message', $methodProphecy, array($call1, $call2)); | ||||
|     } | ||||
|  | ||||
|     function it_is_PredictionException() | ||||
|     { | ||||
|         $this->shouldHaveType('Prophecy\Exception\Prediction\PredictionException'); | ||||
|     } | ||||
|  | ||||
|     function it_extends_MethodProphecyException() | ||||
|     { | ||||
|         $this->shouldHaveType('Prophecy\Exception\Prophecy\MethodProphecyException'); | ||||
|     } | ||||
|  | ||||
|     function it_should_expose_calls_list_through_getter($call1, $call2) | ||||
|     { | ||||
|         $this->getCalls()->shouldReturn(array($call1, $call2)); | ||||
|     } | ||||
| } | ||||
| @@ -1,30 +0,0 @@ | ||||
| <?php | ||||
|  | ||||
| namespace spec\Prophecy\Exception\Prophecy; | ||||
|  | ||||
| use PhpSpec\ObjectBehavior; | ||||
| use spec\Prophecy\Exception\Prophecy; | ||||
|  | ||||
| class MethodProphecyExceptionSpec extends ObjectBehavior | ||||
| { | ||||
|     /** | ||||
|      * @param \Prophecy\Prophecy\ObjectProphecy $objectProphecy | ||||
|      * @param \Prophecy\Prophecy\MethodProphecy $methodProphecy | ||||
|      */ | ||||
|     function let($objectProphecy, $methodProphecy) | ||||
|     { | ||||
|         $methodProphecy->getObjectProphecy()->willReturn($objectProphecy); | ||||
|  | ||||
|         $this->beConstructedWith('message', $methodProphecy); | ||||
|     } | ||||
|  | ||||
|     function it_extends_DoubleException() | ||||
|     { | ||||
|         $this->shouldBeAnInstanceOf('Prophecy\Exception\Prophecy\ObjectProphecyException'); | ||||
|     } | ||||
|  | ||||
|     function it_holds_a_stub_reference($methodProphecy) | ||||
|     { | ||||
|         $this->getMethodProphecy()->shouldReturn($methodProphecy); | ||||
|     } | ||||
| } | ||||
| @@ -1,27 +0,0 @@ | ||||
| <?php | ||||
|  | ||||
| namespace spec\Prophecy\Exception\Prophecy; | ||||
|  | ||||
| use PhpSpec\ObjectBehavior; | ||||
| use spec\Prophecy\Exception\Prophecy; | ||||
|  | ||||
| class ObjectProphecyExceptionSpec extends ObjectBehavior | ||||
| { | ||||
|     /** | ||||
|      * @param \Prophecy\Prophecy\ObjectProphecy $objectProphecy | ||||
|      */ | ||||
|     function let($objectProphecy) | ||||
|     { | ||||
|         $this->beConstructedWith('message', $objectProphecy); | ||||
|     } | ||||
|  | ||||
|     function it_should_be_a_prophecy_exception() | ||||
|     { | ||||
|         $this->shouldBeAnInstanceOf('Prophecy\Exception\Prophecy\ProphecyException'); | ||||
|     } | ||||
|  | ||||
|     function it_holds_double_reference($objectProphecy) | ||||
|     { | ||||
|         $this->getObjectProphecy()->shouldReturn($objectProphecy); | ||||
|     } | ||||
| } | ||||
| @@ -1,42 +0,0 @@ | ||||
| <?php | ||||
|  | ||||
| namespace spec\Prophecy\Prediction; | ||||
|  | ||||
| use PhpSpec\ObjectBehavior; | ||||
| use Prophecy\Argument; | ||||
|  | ||||
| class CallPredictionSpec extends ObjectBehavior | ||||
| { | ||||
|     function it_is_prediction() | ||||
|     { | ||||
|         $this->shouldHaveType('Prophecy\Prediction\PredictionInterface'); | ||||
|     } | ||||
|  | ||||
|     /** | ||||
|      * @param \Prophecy\Prophecy\ObjectProphecy $object | ||||
|      * @param \Prophecy\Prophecy\MethodProphecy $method | ||||
|      * @param \Prophecy\Call\Call               $call | ||||
|      */ | ||||
|     function it_does_nothing_if_there_is_more_than_one_call_been_made($object, $method, $call) | ||||
|     { | ||||
|         $this->check(array($call), $object, $method)->shouldReturn(null); | ||||
|     } | ||||
|  | ||||
|     /** | ||||
|      * @param \Prophecy\Prophecy\ObjectProphecy    $object | ||||
|      * @param \Prophecy\Prophecy\MethodProphecy    $method | ||||
|      * @param \Prophecy\Argument\ArgumentsWildcard $arguments | ||||
|      */ | ||||
|     function it_throws_NoCallsException_if_no_calls_found($object, $method, $arguments) | ||||
|     { | ||||
|         $method->getObjectProphecy()->willReturn($object); | ||||
|         $method->getMethodName()->willReturn('getName'); | ||||
|         $method->getArgumentsWildcard()->willReturn($arguments); | ||||
|         $arguments->__toString()->willReturn('123'); | ||||
|         $object->reveal()->willReturn(new \stdClass()); | ||||
|         $object->findProphecyMethodCalls('getName', Argument::any())->willReturn(array()); | ||||
|  | ||||
|         $this->shouldThrow('Prophecy\Exception\Prediction\NoCallsException') | ||||
|             ->duringCheck(array(), $object, $method); | ||||
|     } | ||||
| } | ||||
| @@ -1,54 +0,0 @@ | ||||
| <?php | ||||
|  | ||||
| namespace spec\Prophecy\Prediction; | ||||
|  | ||||
| use PhpSpec\ObjectBehavior; | ||||
|  | ||||
| class CallTimesPredictionSpec extends ObjectBehavior | ||||
| { | ||||
|     function let() | ||||
|     { | ||||
|         $this->beConstructedWith(2); | ||||
|     } | ||||
|  | ||||
|     function it_is_prediction() | ||||
|     { | ||||
|         $this->shouldHaveType('Prophecy\Prediction\PredictionInterface'); | ||||
|     } | ||||
|  | ||||
|     /** | ||||
|      * @param \Prophecy\Prophecy\ObjectProphecy $object | ||||
|      * @param \Prophecy\Prophecy\MethodProphecy $method | ||||
|      * @param \Prophecy\Call\Call               $call1 | ||||
|      * @param \Prophecy\Call\Call               $call2 | ||||
|      */ | ||||
|     function it_does_nothing_if_there_were_exact_amount_of_calls_being_made( | ||||
|         $object, $method, $call1, $call2 | ||||
|     ) | ||||
|     { | ||||
|         $this->check(array($call1, $call2), $object, $method)->shouldReturn(null); | ||||
|     } | ||||
|  | ||||
|     /** | ||||
|      * @param \Prophecy\Prophecy\ObjectProphecy    $object | ||||
|      * @param \Prophecy\Prophecy\MethodProphecy    $method | ||||
|      * @param \Prophecy\Call\Call                  $call | ||||
|      * @param \Prophecy\Argument\ArgumentsWildcard $arguments | ||||
|      */ | ||||
|     function it_throws_UnexpectedCallsCountException_if_calls_found( | ||||
|         $object, $method, $call, $arguments | ||||
|     ) | ||||
|     { | ||||
|         $method->getObjectProphecy()->willReturn($object); | ||||
|         $method->getMethodName()->willReturn('getName'); | ||||
|         $method->getArgumentsWildcard()->willReturn($arguments); | ||||
|         $arguments->__toString()->willReturn('123'); | ||||
|  | ||||
|         $call->getMethodName()->willReturn('getName'); | ||||
|         $call->getArguments()->willReturn(array(5, 4, 'three')); | ||||
|         $call->getCallPlace()->willReturn('unknown'); | ||||
|  | ||||
|         $this->shouldThrow('Prophecy\Exception\Prediction\UnexpectedCallsCountException') | ||||
|             ->duringCheck(array($call), $object, $method); | ||||
|     } | ||||
| } | ||||
| @@ -1,36 +0,0 @@ | ||||
| <?php | ||||
|  | ||||
| namespace spec\Prophecy\Prediction; | ||||
|  | ||||
| use PhpSpec\ObjectBehavior; | ||||
|  | ||||
| use RuntimeException; | ||||
|  | ||||
| class CallbackPredictionSpec extends ObjectBehavior | ||||
| { | ||||
|     function let() | ||||
|     { | ||||
|         $this->beConstructedWith('get_class'); | ||||
|     } | ||||
|  | ||||
|     function it_is_prediction() | ||||
|     { | ||||
|         $this->shouldHaveType('Prophecy\Prediction\PredictionInterface'); | ||||
|     } | ||||
|  | ||||
|     /** | ||||
|      * @param \Prophecy\Prophecy\ObjectProphecy $object | ||||
|      * @param \Prophecy\Prophecy\MethodProphecy $method | ||||
|      * @param \Prophecy\Call\Call               $call | ||||
|      */ | ||||
|     function it_proxies_call_to_callback($object, $method, $call) | ||||
|     { | ||||
|         $returnFirstCallCallback = function ($calls, $object, $method) { | ||||
|             throw new RuntimeException; | ||||
|         }; | ||||
|  | ||||
|         $this->beConstructedWith($returnFirstCallCallback); | ||||
|  | ||||
|         $this->shouldThrow('RuntimeException')->duringCheck(array($call), $object, $method); | ||||
|     } | ||||
| } | ||||
| @@ -1,43 +0,0 @@ | ||||
| <?php | ||||
|  | ||||
| namespace spec\Prophecy\Prediction; | ||||
|  | ||||
| use PhpSpec\ObjectBehavior; | ||||
|  | ||||
| class NoCallsPredictionSpec extends ObjectBehavior | ||||
| { | ||||
|     function it_is_prediction() | ||||
|     { | ||||
|         $this->shouldHaveType('Prophecy\Prediction\PredictionInterface'); | ||||
|     } | ||||
|  | ||||
|     /** | ||||
|      * @param \Prophecy\Prophecy\ObjectProphecy $object | ||||
|      * @param \Prophecy\Prophecy\MethodProphecy $method | ||||
|      */ | ||||
|     function it_does_nothing_if_there_is_no_calls_made($object, $method) | ||||
|     { | ||||
|         $this->check(array(), $object, $method)->shouldReturn(null); | ||||
|     } | ||||
|  | ||||
|     /** | ||||
|      * @param \Prophecy\Prophecy\ObjectProphecy    $object | ||||
|      * @param \Prophecy\Prophecy\MethodProphecy    $method | ||||
|      * @param \Prophecy\Call\Call                  $call | ||||
|      * @param \Prophecy\Argument\ArgumentsWildcard $arguments | ||||
|      */ | ||||
|     function it_throws_UnexpectedCallsException_if_calls_found($object, $method, $call, $arguments) | ||||
|     { | ||||
|         $method->getObjectProphecy()->willReturn($object); | ||||
|         $method->getMethodName()->willReturn('getName'); | ||||
|         $method->getArgumentsWildcard()->willReturn($arguments); | ||||
|         $arguments->__toString()->willReturn('123'); | ||||
|  | ||||
|         $call->getMethodName()->willReturn('getName'); | ||||
|         $call->getArguments()->willReturn(array(5, 4, 'three')); | ||||
|         $call->getCallPlace()->willReturn('unknown'); | ||||
|  | ||||
|         $this->shouldThrow('Prophecy\Exception\Prediction\UnexpectedCallsException') | ||||
|             ->duringCheck(array($call), $object, $method); | ||||
|     } | ||||
| } | ||||
| @@ -1,110 +0,0 @@ | ||||
| <?php | ||||
|  | ||||
| namespace spec\Prophecy\Promise; | ||||
|  | ||||
| use PhpSpec\ObjectBehavior; | ||||
|  | ||||
| class CallbackPromiseSpec extends ObjectBehavior | ||||
| { | ||||
|     function let() | ||||
|     { | ||||
|         $this->beConstructedWith('get_class'); | ||||
|     } | ||||
|  | ||||
|     function it_is_promise() | ||||
|     { | ||||
|         $this->shouldBeAnInstanceOf('Prophecy\Promise\PromiseInterface'); | ||||
|     } | ||||
|  | ||||
|     /** | ||||
|      * @param \Prophecy\Prophecy\ObjectProphecy $object | ||||
|      * @param \Prophecy\Prophecy\MethodProphecy $method | ||||
|      */ | ||||
|     function it_should_execute_closure_callback($object, $method) | ||||
|     { | ||||
|         $firstArgumentCallback = function ($args) { | ||||
|             return $args[0]; | ||||
|         }; | ||||
|  | ||||
|         $this->beConstructedWith($firstArgumentCallback); | ||||
|  | ||||
|         $this->execute(array('one', 'two'), $object, $method)->shouldReturn('one'); | ||||
|     } | ||||
|  | ||||
|     /** | ||||
|      * @param \Prophecy\Prophecy\ObjectProphecy $object | ||||
|      * @param \Prophecy\Prophecy\MethodProphecy $method | ||||
|      */ | ||||
|     function it_should_execute_static_array_callback($object, $method) | ||||
|     { | ||||
|         $firstArgumentCallback = array('spec\Prophecy\Promise\ClassCallback', 'staticCallbackMethod'); | ||||
|  | ||||
|         $this->beConstructedWith($firstArgumentCallback); | ||||
|  | ||||
|         $this->execute(array('one', 'two'), $object, $method)->shouldReturn('one'); | ||||
|     } | ||||
|  | ||||
|     /** | ||||
|      * @param \Prophecy\Prophecy\ObjectProphecy $object | ||||
|      * @param \Prophecy\Prophecy\MethodProphecy $method | ||||
|      */ | ||||
|     function it_should_execute_instance_array_callback($object, $method) | ||||
|     { | ||||
|         $class = new ClassCallback(); | ||||
|         $firstArgumentCallback = array($class, 'callbackMethod'); | ||||
|  | ||||
|         $this->beConstructedWith($firstArgumentCallback); | ||||
|  | ||||
|         $this->execute(array('one', 'two'), $object, $method)->shouldReturn('one'); | ||||
|     } | ||||
|  | ||||
|     /** | ||||
|      * @param \Prophecy\Prophecy\ObjectProphecy $object | ||||
|      * @param \Prophecy\Prophecy\MethodProphecy $method | ||||
|      */ | ||||
|     function it_should_execute_string_function_callback($object, $method) | ||||
|     { | ||||
|         $firstArgumentCallback = 'spec\Prophecy\Promise\functionCallbackFirstArgument'; | ||||
|  | ||||
|         $this->beConstructedWith($firstArgumentCallback); | ||||
|  | ||||
|         $this->execute(array('one', 'two'), $object, $method)->shouldReturn('one'); | ||||
|     } | ||||
|  | ||||
| } | ||||
|  | ||||
| /** | ||||
|  * Class used to test callbackpromise | ||||
|  * | ||||
|  * @param array | ||||
|  * @return string | ||||
|  */ | ||||
| class ClassCallback | ||||
| { | ||||
|     /** | ||||
|      * @param array $args | ||||
|      */ | ||||
|     function callbackMethod($args) | ||||
|     { | ||||
|         return $args[0]; | ||||
|     } | ||||
|  | ||||
|     /** | ||||
|      * @param array $args | ||||
|      */ | ||||
|     static function staticCallbackMethod($args) | ||||
|     { | ||||
|         return $args[0]; | ||||
|     } | ||||
| } | ||||
|  | ||||
| /** | ||||
|  * Callback function used to test callbackpromise | ||||
|  * | ||||
|  * @param array | ||||
|  * @return string | ||||
|  */ | ||||
| function functionCallbackFirstArgument($args) | ||||
| { | ||||
|     return $args[0]; | ||||
| } | ||||
| @@ -1,41 +0,0 @@ | ||||
| <?php | ||||
|  | ||||
| namespace spec\Prophecy\Promise; | ||||
|  | ||||
| use PhpSpec\ObjectBehavior; | ||||
|  | ||||
| class ReturnArgumentPromiseSpec extends ObjectBehavior | ||||
| { | ||||
|     function it_is_promise() | ||||
|     { | ||||
|         $this->shouldBeAnInstanceOf('Prophecy\Promise\PromiseInterface'); | ||||
|     } | ||||
|  | ||||
|     /** | ||||
|      * @param \Prophecy\Prophecy\ObjectProphecy $object | ||||
|      * @param \Prophecy\Prophecy\MethodProphecy $method | ||||
|      */ | ||||
|     function it_should_return_first_argument_if_provided($object, $method) | ||||
|     { | ||||
|         $this->execute(array('one', 'two'), $object, $method)->shouldReturn('one'); | ||||
|     } | ||||
|  | ||||
|     /** | ||||
|      * @param \Prophecy\Prophecy\ObjectProphecy $object | ||||
|      * @param \Prophecy\Prophecy\MethodProphecy $method | ||||
|      */ | ||||
|     function it_should_return_null_if_no_arguments_provided($object, $method) | ||||
|     { | ||||
|         $this->execute(array(), $object, $method)->shouldReturn(null); | ||||
|     } | ||||
|  | ||||
|     /** | ||||
|      * @param \Prophecy\Prophecy\ObjectProphecy $object | ||||
|      * @param \Prophecy\Prophecy\MethodProphecy $method | ||||
|      */ | ||||
|     function it_should_return_nth_argument_if_provided($object, $method) | ||||
|     { | ||||
|         $this->beConstructedWith(1); | ||||
|         $this->execute(array('one', 'two'), $object, $method)->shouldReturn('two'); | ||||
|     } | ||||
| } | ||||
| @@ -1,61 +0,0 @@ | ||||
| <?php | ||||
|  | ||||
| namespace spec\Prophecy\Promise; | ||||
|  | ||||
| use PhpSpec\ObjectBehavior; | ||||
|  | ||||
| class ReturnPromiseSpec extends ObjectBehavior | ||||
| { | ||||
|     function let() | ||||
|     { | ||||
|         $this->beConstructedWith(array(42)); | ||||
|     } | ||||
|  | ||||
|     function it_is_promise() | ||||
|     { | ||||
|         $this->shouldBeAnInstanceOf('Prophecy\Promise\PromiseInterface'); | ||||
|     } | ||||
|  | ||||
|     /** | ||||
|      * @param \Prophecy\Prophecy\ObjectProphecy $object | ||||
|      * @param \Prophecy\Prophecy\MethodProphecy $method | ||||
|      */ | ||||
|     function it_returns_value_it_was_constructed_with($object, $method) | ||||
|     { | ||||
|         $this->execute(array(), $object, $method)->shouldReturn(42); | ||||
|     } | ||||
|  | ||||
|     /** | ||||
|      * @param \Prophecy\Prophecy\ObjectProphecy $object | ||||
|      * @param \Prophecy\Prophecy\MethodProphecy $method | ||||
|      */ | ||||
|     function it_always_returns_last_value_left_in_the_return_values($object, $method) | ||||
|     { | ||||
|         $this->execute(array(), $object, $method)->shouldReturn(42); | ||||
|         $this->execute(array(), $object, $method)->shouldReturn(42); | ||||
|     } | ||||
|  | ||||
|     /** | ||||
|      * @param \Prophecy\Prophecy\ObjectProphecy $object | ||||
|      * @param \Prophecy\Prophecy\MethodProphecy $method | ||||
|      */ | ||||
|     function it_consequently_returns_multiple_values_it_was_constructed_with($object, $method) | ||||
|     { | ||||
|         $this->beConstructedWith(array(42, 24, 12)); | ||||
|  | ||||
|         $this->execute(array(), $object, $method)->shouldReturn(42); | ||||
|         $this->execute(array(), $object, $method)->shouldReturn(24); | ||||
|         $this->execute(array(), $object, $method)->shouldReturn(12); | ||||
|     } | ||||
|  | ||||
|     /** | ||||
|      * @param \Prophecy\Prophecy\ObjectProphecy $object | ||||
|      * @param \Prophecy\Prophecy\MethodProphecy $method | ||||
|      */ | ||||
|     function it_returns_null_if_constructed_with_empty_array($object, $method) | ||||
|     { | ||||
|         $this->beConstructedWith(array()); | ||||
|  | ||||
|         $this->execute(array(), $object, $method)->shouldReturn(null); | ||||
|     } | ||||
| } | ||||
| @@ -1,58 +0,0 @@ | ||||
| <?php | ||||
|  | ||||
| namespace spec\Prophecy\Promise; | ||||
|  | ||||
| use PhpSpec\ObjectBehavior; | ||||
|  | ||||
| class ThrowPromiseSpec extends ObjectBehavior | ||||
| { | ||||
|     function let() | ||||
|     { | ||||
|         $this->beConstructedWith('RuntimeException'); | ||||
|     } | ||||
|  | ||||
|     function it_is_promise() | ||||
|     { | ||||
|         $this->shouldBeAnInstanceOf('Prophecy\Promise\PromiseInterface'); | ||||
|     } | ||||
|  | ||||
|     /** | ||||
|      * @param \Prophecy\Prophecy\ObjectProphecy $object | ||||
|      * @param \Prophecy\Prophecy\MethodProphecy $method | ||||
|      */ | ||||
|     function it_instantiates_and_throws_exception_from_provided_classname($object, $method) | ||||
|     { | ||||
|         $this->beConstructedWith('InvalidArgumentException'); | ||||
|  | ||||
|         $this->shouldThrow('InvalidArgumentException') | ||||
|             ->duringExecute(array(), $object, $method); | ||||
|     } | ||||
|  | ||||
|     /** | ||||
|      * @param \Prophecy\Prophecy\ObjectProphecy $object | ||||
|      * @param \Prophecy\Prophecy\MethodProphecy $method | ||||
|      */ | ||||
|     function it_instantiates_exceptions_with_required_arguments($object, $method) | ||||
|     { | ||||
|         $this->beConstructedWith('spec\Prophecy\Promise\RequiredArgumentException'); | ||||
|  | ||||
|         $this->shouldThrow('spec\Prophecy\Promise\RequiredArgumentException') | ||||
|             ->duringExecute(array(), $object, $method); | ||||
|     } | ||||
|  | ||||
|     /** | ||||
|      * @param \Prophecy\Prophecy\ObjectProphecy $object | ||||
|      * @param \Prophecy\Prophecy\MethodProphecy $method | ||||
|      */ | ||||
|     function it_throws_provided_exception($object, $method) | ||||
|     { | ||||
|         $this->beConstructedWith($exc = new \RuntimeException('Some exception')); | ||||
|  | ||||
|         $this->shouldThrow($exc)->duringExecute(array(), $object, $method); | ||||
|     } | ||||
| } | ||||
|  | ||||
| class RequiredArgumentException extends \Exception | ||||
| { | ||||
|     final public function __construct($message, $code) {} | ||||
| } | ||||
| @@ -1,381 +0,0 @@ | ||||
| <?php | ||||
|  | ||||
| namespace spec\Prophecy\Prophecy; | ||||
|  | ||||
| use PhpSpec\ObjectBehavior; | ||||
|  | ||||
| class MethodProphecySpec extends ObjectBehavior | ||||
| { | ||||
|     /** | ||||
|      * @param \Prophecy\Prophecy\ObjectProphecy $objectProphecy | ||||
|      * @param \ReflectionClass                  $reflection | ||||
|      */ | ||||
|     function let($objectProphecy, $reflection) | ||||
|     { | ||||
|         $objectProphecy->reveal()->willReturn($reflection); | ||||
|  | ||||
|         $this->beConstructedWith($objectProphecy, 'getName', null); | ||||
|     } | ||||
|  | ||||
|     function it_is_initializable() | ||||
|     { | ||||
|         $this->shouldHaveType('Prophecy\Prophecy\MethodProphecy'); | ||||
|     } | ||||
|  | ||||
|     function its_constructor_throws_MethodNotFoundException_for_unexisting_method($objectProphecy) | ||||
|     { | ||||
|         $this->shouldThrow('Prophecy\Exception\Doubler\MethodNotFoundException')->during( | ||||
|             '__construct', array($objectProphecy, 'getUnexisting', null) | ||||
|         ); | ||||
|     } | ||||
|  | ||||
|     function its_constructor_throws_MethodProphecyException_for_final_methods($objectProphecy, ClassWithFinalMethod $subject) | ||||
|     { | ||||
|         $objectProphecy->reveal()->willReturn($subject); | ||||
|  | ||||
|         $this->shouldThrow('Prophecy\Exception\Prophecy\MethodProphecyException')->during( | ||||
|             '__construct', array($objectProphecy, 'finalMethod', null) | ||||
|         ); | ||||
|     } | ||||
|  | ||||
|     function its_constructor_transforms_array_passed_as_3rd_argument_to_ArgumentsWildcard( | ||||
|         $objectProphecy | ||||
|     ) | ||||
|     { | ||||
|         $this->beConstructedWith($objectProphecy, 'getName', array(42, 33)); | ||||
|  | ||||
|         $wildcard = $this->getArgumentsWildcard(); | ||||
|         $wildcard->shouldNotBe(null); | ||||
|         $wildcard->__toString()->shouldReturn('exact(42), exact(33)'); | ||||
|     } | ||||
|  | ||||
|     function its_constructor_does_not_touch_third_argument_if_it_is_null($objectProphecy) | ||||
|     { | ||||
|         $this->beConstructedWith($objectProphecy, 'getName', null); | ||||
|  | ||||
|         $wildcard = $this->getArgumentsWildcard(); | ||||
|         $wildcard->shouldBe(null); | ||||
|     } | ||||
|  | ||||
|     /** | ||||
|      * @param \Prophecy\Promise\PromiseInterface $promise | ||||
|      */ | ||||
|     function it_records_promise_through_will_method($promise, $objectProphecy) | ||||
|     { | ||||
|         $objectProphecy->addMethodProphecy($this)->willReturn(null); | ||||
|  | ||||
|         $this->will($promise); | ||||
|         $this->getPromise()->shouldReturn($promise); | ||||
|     } | ||||
|  | ||||
|     /** | ||||
|      * @param \Prophecy\Promise\PromiseInterface $promise | ||||
|      */ | ||||
|     function it_adds_itself_to_ObjectProphecy_during_call_to_will($objectProphecy, $promise) | ||||
|     { | ||||
|         $objectProphecy->addMethodProphecy($this)->shouldBeCalled(); | ||||
|  | ||||
|         $this->will($promise); | ||||
|     } | ||||
|  | ||||
|     function it_adds_ReturnPromise_during_willReturn_call($objectProphecy) | ||||
|     { | ||||
|         $objectProphecy->addMethodProphecy($this)->willReturn(null); | ||||
|  | ||||
|         $this->willReturn(42); | ||||
|         $this->getPromise()->shouldBeAnInstanceOf('Prophecy\Promise\ReturnPromise'); | ||||
|     } | ||||
|  | ||||
|     function it_adds_ThrowPromise_during_willThrow_call($objectProphecy) | ||||
|     { | ||||
|         $objectProphecy->addMethodProphecy($this)->willReturn(null); | ||||
|  | ||||
|         $this->willThrow('RuntimeException'); | ||||
|         $this->getPromise()->shouldBeAnInstanceOf('Prophecy\Promise\ThrowPromise'); | ||||
|     } | ||||
|  | ||||
|     function it_adds_ReturnArgumentPromise_during_willReturnArgument_call($objectProphecy) | ||||
|     { | ||||
|         $objectProphecy->addMethodProphecy($this)->willReturn(null); | ||||
|  | ||||
|         $this->willReturnArgument(); | ||||
|         $this->getPromise()->shouldBeAnInstanceOf('Prophecy\Promise\ReturnArgumentPromise'); | ||||
|     } | ||||
|  | ||||
|     function it_adds_ReturnArgumentPromise_during_willReturnArgument_call_with_index_argument($objectProphecy) | ||||
|     { | ||||
|         $objectProphecy->addMethodProphecy($this)->willReturn(null); | ||||
|  | ||||
|         $this->willReturnArgument(1); | ||||
|         $promise = $this->getPromise(); | ||||
|         $promise->shouldBeAnInstanceOf('Prophecy\Promise\ReturnArgumentPromise'); | ||||
|         $promise->execute(array('one', 'two'), $objectProphecy, $this)->shouldReturn('two'); | ||||
|     } | ||||
|  | ||||
|     function it_adds_CallbackPromise_during_will_call_with_callback_argument($objectProphecy) | ||||
|     { | ||||
|         $objectProphecy->addMethodProphecy($this)->willReturn(null); | ||||
|  | ||||
|         $callback = function () {}; | ||||
|  | ||||
|         $this->will($callback); | ||||
|         $this->getPromise()->shouldBeAnInstanceOf('Prophecy\Promise\CallbackPromise'); | ||||
|     } | ||||
|  | ||||
|     /** | ||||
|      * @param \Prophecy\Prediction\PredictionInterface $prediction | ||||
|      */ | ||||
|     function it_records_prediction_through_should_method($prediction, $objectProphecy) | ||||
|     { | ||||
|         $objectProphecy->addMethodProphecy($this)->willReturn(null); | ||||
|  | ||||
|         $this->callOnWrappedObject('should', array($prediction)); | ||||
|         $this->getPrediction()->shouldReturn($prediction); | ||||
|     } | ||||
|  | ||||
|     function it_adds_CallbackPrediction_during_should_call_with_callback_argument($objectProphecy) | ||||
|     { | ||||
|         $objectProphecy->addMethodProphecy($this)->willReturn(null); | ||||
|  | ||||
|         $callback = function () {}; | ||||
|  | ||||
|         $this->callOnWrappedObject('should', array($callback)); | ||||
|         $this->getPrediction()->shouldBeAnInstanceOf('Prophecy\Prediction\CallbackPrediction'); | ||||
|     } | ||||
|  | ||||
|     /** | ||||
|      * @param \Prophecy\Prediction\PredictionInterface $prediction | ||||
|      */ | ||||
|     function it_adds_itself_to_ObjectProphecy_during_call_to_should($objectProphecy, $prediction) | ||||
|     { | ||||
|         $objectProphecy->addMethodProphecy($this)->shouldBeCalled(); | ||||
|  | ||||
|         $this->callOnWrappedObject('should', array($prediction)); | ||||
|     } | ||||
|  | ||||
|     function it_adds_CallPrediction_during_shouldBeCalled_call($objectProphecy) | ||||
|     { | ||||
|         $objectProphecy->addMethodProphecy($this)->willReturn(null); | ||||
|  | ||||
|         $this->callOnWrappedObject('shouldBeCalled', array()); | ||||
|         $this->getPrediction()->shouldBeAnInstanceOf('Prophecy\Prediction\CallPrediction'); | ||||
|     } | ||||
|  | ||||
|     function it_adds_NoCallsPrediction_during_shouldNotBeCalled_call($objectProphecy) | ||||
|     { | ||||
|         $objectProphecy->addMethodProphecy($this)->willReturn(null); | ||||
|  | ||||
|         $this->callOnWrappedObject('shouldNotBeCalled', array()); | ||||
|         $this->getPrediction()->shouldBeAnInstanceOf('Prophecy\Prediction\NoCallsPrediction'); | ||||
|     } | ||||
|  | ||||
|     function it_adds_CallTimesPrediction_during_shouldBeCalledTimes_call($objectProphecy) | ||||
|     { | ||||
|         $objectProphecy->addMethodProphecy($this)->willReturn(null); | ||||
|  | ||||
|         $this->callOnWrappedObject('shouldBeCalledTimes', array(5)); | ||||
|         $this->getPrediction()->shouldBeAnInstanceOf('Prophecy\Prediction\CallTimesPrediction'); | ||||
|     } | ||||
|  | ||||
|     /** | ||||
|      * @param \Prophecy\Argument\ArgumentsWildcard     $arguments | ||||
|      * @param \Prophecy\Prediction\PredictionInterface $prediction | ||||
|      * @param \Prophecy\Call\Call                      $call1 | ||||
|      * @param \Prophecy\Call\Call                      $call2 | ||||
|      */ | ||||
|     function it_checks_prediction_via_shouldHave_method_call( | ||||
|         $objectProphecy, $arguments, $prediction, $call1, $call2 | ||||
|     ) | ||||
|     { | ||||
|         $objectProphecy->addMethodProphecy($this)->willReturn(null); | ||||
|         $prediction->check(array($call1, $call2), $objectProphecy->getWrappedObject(), $this)->shouldBeCalled(); | ||||
|         $objectProphecy->findProphecyMethodCalls('getName', $arguments)->willReturn(array($call1, $call2)); | ||||
|  | ||||
|         $this->withArguments($arguments); | ||||
|         $this->callOnWrappedObject('shouldHave', array($prediction)); | ||||
|     } | ||||
|  | ||||
|     /** | ||||
|      * @param \Prophecy\Argument\ArgumentsWildcard     $arguments | ||||
|      * @param \Prophecy\Prediction\PredictionInterface $prediction | ||||
|      * @param \Prophecy\Call\Call                      $call1 | ||||
|      * @param \Prophecy\Call\Call                      $call2 | ||||
|      */ | ||||
|     function it_sets_return_promise_during_shouldHave_call_if_none_was_set_before( | ||||
|         $objectProphecy, $arguments, $prediction, $call1, $call2 | ||||
|     ) | ||||
|     { | ||||
|         $objectProphecy->addMethodProphecy($this)->willReturn(null); | ||||
|         $prediction->check(array($call1, $call2), $objectProphecy->getWrappedObject(), $this)->shouldBeCalled(); | ||||
|         $objectProphecy->findProphecyMethodCalls('getName', $arguments)->willReturn(array($call1, $call2)); | ||||
|  | ||||
|         $this->withArguments($arguments); | ||||
|         $this->callOnWrappedObject('shouldHave', array($prediction)); | ||||
|  | ||||
|         $this->getPromise()->shouldReturnAnInstanceOf('Prophecy\Promise\ReturnPromise'); | ||||
|     } | ||||
|  | ||||
|     /** | ||||
|      * @param \Prophecy\Argument\ArgumentsWildcard     $arguments | ||||
|      * @param \Prophecy\Prediction\PredictionInterface $prediction | ||||
|      * @param \Prophecy\Call\Call                      $call1 | ||||
|      * @param \Prophecy\Call\Call                      $call2 | ||||
|      * @param \Prophecy\Promise\PromiseInterface       $promise | ||||
|      */ | ||||
|     function it_does_not_set_return_promise_during_shouldHave_call_if_it_was_set_before( | ||||
|         $objectProphecy, $arguments, $prediction, $call1, $call2, $promise | ||||
|     ) | ||||
|     { | ||||
|         $objectProphecy->addMethodProphecy($this)->willReturn(null); | ||||
|         $prediction->check(array($call1, $call2), $objectProphecy->getWrappedObject(), $this)->shouldBeCalled(); | ||||
|         $objectProphecy->findProphecyMethodCalls('getName', $arguments)->willReturn(array($call1, $call2)); | ||||
|  | ||||
|         $this->will($promise); | ||||
|         $this->withArguments($arguments); | ||||
|         $this->callOnWrappedObject('shouldHave', array($prediction)); | ||||
|  | ||||
|         $this->getPromise()->shouldReturn($promise); | ||||
|     } | ||||
|  | ||||
|     /** | ||||
|      * @param \Prophecy\Argument\ArgumentsWildcard     $arguments | ||||
|      * @param \Prophecy\Prediction\PredictionInterface $prediction1 | ||||
|      * @param \Prophecy\Prediction\PredictionInterface $prediction2 | ||||
|      * @param \Prophecy\Call\Call                      $call1 | ||||
|      * @param \Prophecy\Call\Call                      $call2 | ||||
|      * @param \Prophecy\Promise\PromiseInterface       $promise | ||||
|      */ | ||||
|     function it_records_checked_predictions( | ||||
|         $objectProphecy, $arguments, $prediction1, $prediction2, $call1, $call2, $promise | ||||
|     ) | ||||
|     { | ||||
|         $objectProphecy->addMethodProphecy($this)->willReturn(null); | ||||
|         $prediction1->check(array($call1, $call2), $objectProphecy->getWrappedObject(), $this)->willReturn(); | ||||
|         $prediction2->check(array($call1, $call2), $objectProphecy->getWrappedObject(), $this)->willReturn(); | ||||
|         $objectProphecy->findProphecyMethodCalls('getName', $arguments)->willReturn(array($call1, $call2)); | ||||
|  | ||||
|         $this->will($promise); | ||||
|         $this->withArguments($arguments); | ||||
|         $this->callOnWrappedObject('shouldHave', array($prediction1)); | ||||
|         $this->callOnWrappedObject('shouldHave', array($prediction2)); | ||||
|  | ||||
|         $this->getCheckedPredictions()->shouldReturn(array($prediction1, $prediction2)); | ||||
|     } | ||||
|  | ||||
|     /** | ||||
|      * @param \Prophecy\Argument\ArgumentsWildcard     $arguments | ||||
|      * @param \Prophecy\Prediction\PredictionInterface $prediction | ||||
|      * @param \Prophecy\Call\Call                      $call1 | ||||
|      * @param \Prophecy\Call\Call                      $call2 | ||||
|      * @param \Prophecy\Promise\PromiseInterface       $promise | ||||
|      */ | ||||
|     function it_records_even_failed_checked_predictions( | ||||
|         $objectProphecy, $arguments, $prediction, $call1, $call2, $promise | ||||
|     ) | ||||
|     { | ||||
|         $objectProphecy->addMethodProphecy($this)->willReturn(null); | ||||
|         $prediction->check(array($call1, $call2), $objectProphecy->getWrappedObject(), $this)->willThrow(new \RuntimeException()); | ||||
|         $objectProphecy->findProphecyMethodCalls('getName', $arguments)->willReturn(array($call1, $call2)); | ||||
|  | ||||
|         $this->will($promise); | ||||
|         $this->withArguments($arguments); | ||||
|  | ||||
|         try { | ||||
|           $this->callOnWrappedObject('shouldHave', array($prediction)); | ||||
|         } catch (\Exception $e) {} | ||||
|  | ||||
|         $this->getCheckedPredictions()->shouldReturn(array($prediction)); | ||||
|     } | ||||
|  | ||||
|     /** | ||||
|      * @param \Prophecy\Argument\ArgumentsWildcard     $arguments | ||||
|      * @param \Prophecy\Prediction\PredictionInterface $prediction | ||||
|      * @param \Prophecy\Call\Call                      $call1 | ||||
|      * @param \Prophecy\Call\Call                      $call2 | ||||
|      */ | ||||
|     function it_checks_prediction_via_shouldHave_method_call_with_callback( | ||||
|         $objectProphecy, $arguments, $prediction, $call1, $call2 | ||||
|     ) | ||||
|     { | ||||
|         $callback = function ($calls, $object, $method) { | ||||
|             throw new \RuntimeException; | ||||
|         }; | ||||
|         $objectProphecy->findProphecyMethodCalls('getName', $arguments)->willReturn(array($call1, $call2)); | ||||
|  | ||||
|         $this->withArguments($arguments); | ||||
|         $this->shouldThrow('RuntimeException')->duringShouldHave($callback); | ||||
|     } | ||||
|  | ||||
|     function it_does_nothing_during_checkPrediction_if_no_prediction_set() | ||||
|     { | ||||
|         $this->checkPrediction()->shouldReturn(null); | ||||
|     } | ||||
|  | ||||
|     /** | ||||
|      * @param \Prophecy\Argument\ArgumentsWildcard     $arguments | ||||
|      * @param \Prophecy\Prediction\PredictionInterface $prediction | ||||
|      * @param \Prophecy\Call\Call                      $call1 | ||||
|      * @param \Prophecy\Call\Call                      $call2 | ||||
|      */ | ||||
|     function it_checks_set_prediction_during_checkPrediction( | ||||
|         $objectProphecy, $arguments, $prediction, $call1, $call2 | ||||
|     ) | ||||
|     { | ||||
|         $prediction->check(array($call1, $call2), $objectProphecy->getWrappedObject(), $this)->shouldBeCalled(); | ||||
|         $objectProphecy->findProphecyMethodCalls('getName', $arguments)->willReturn(array($call1, $call2)); | ||||
|         $objectProphecy->addMethodProphecy($this)->willReturn(null); | ||||
|  | ||||
|         $this->withArguments($arguments); | ||||
|         $this->callOnWrappedObject('should', array($prediction)); | ||||
|         $this->checkPrediction(); | ||||
|     } | ||||
|  | ||||
|     function it_links_back_to_ObjectProphecy_through_getter($objectProphecy) | ||||
|     { | ||||
|         $this->getObjectProphecy()->shouldReturn($objectProphecy); | ||||
|     } | ||||
|  | ||||
|     function it_has_MethodName() | ||||
|     { | ||||
|         $this->getMethodName()->shouldReturn('getName'); | ||||
|     } | ||||
|  | ||||
|     /** | ||||
|      * @param \Prophecy\Argument\ArgumentsWildcard $wildcard | ||||
|      */ | ||||
|     function it_contains_ArgumentsWildcard_it_was_constructed_with($objectProphecy, $wildcard) | ||||
|     { | ||||
|         $this->beConstructedWith($objectProphecy, 'getName', $wildcard); | ||||
|  | ||||
|         $this->getArgumentsWildcard()->shouldReturn($wildcard); | ||||
|     } | ||||
|  | ||||
|     /** | ||||
|      * @param \Prophecy\Argument\ArgumentsWildcard $wildcard | ||||
|      */ | ||||
|     function its_ArgumentWildcard_is_mutable_through_setter($wildcard) | ||||
|     { | ||||
|         $this->withArguments($wildcard); | ||||
|  | ||||
|         $this->getArgumentsWildcard()->shouldReturn($wildcard); | ||||
|     } | ||||
|  | ||||
|     function its_withArguments_transforms_passed_array_into_ArgumentsWildcard() | ||||
|     { | ||||
|         $this->withArguments(array(42, 33)); | ||||
|  | ||||
|         $wildcard = $this->getArgumentsWildcard(); | ||||
|         $wildcard->shouldNotBe(null); | ||||
|         $wildcard->__toString()->shouldReturn('exact(42), exact(33)'); | ||||
|     } | ||||
|  | ||||
|     function its_withArguments_throws_exception_if_wrong_arguments_provided() | ||||
|     { | ||||
|         $this->shouldThrow('Prophecy\Exception\InvalidArgumentException')->duringWithArguments(42); | ||||
|     } | ||||
| } | ||||
|  | ||||
| class ClassWithFinalMethod | ||||
| { | ||||
|     final public function finalMethod() {} | ||||
| } | ||||
| @@ -1,319 +0,0 @@ | ||||
| <?php | ||||
|  | ||||
| namespace spec\Prophecy\Prophecy; | ||||
|  | ||||
| use PhpSpec\ObjectBehavior; | ||||
| use Prophecy\Argument; | ||||
|  | ||||
| class ObjectProphecySpec extends ObjectBehavior | ||||
| { | ||||
|     /** | ||||
|      * @param \Prophecy\Doubler\LazyDouble                $lazyDouble | ||||
|      * @param \Prophecy\Prophecy\ProphecySubjectInterface $double | ||||
|      */ | ||||
|     function let($lazyDouble, $double) | ||||
|     { | ||||
|         $this->beConstructedWith($lazyDouble); | ||||
|  | ||||
|         $lazyDouble->getInstance()->willReturn($double); | ||||
|     } | ||||
|  | ||||
|     function it_implements_ProphecyInterface() | ||||
|     { | ||||
|         $this->shouldBeAnInstanceOf('Prophecy\Prophecy\ProphecyInterface'); | ||||
|     } | ||||
|  | ||||
|     function it_sets_parentClass_during_willExtend_call($lazyDouble) | ||||
|     { | ||||
|         $lazyDouble->setParentClass('123')->shouldBeCalled(); | ||||
|  | ||||
|         $this->willExtend('123'); | ||||
|     } | ||||
|  | ||||
|     function it_adds_interface_during_willImplement_call($lazyDouble) | ||||
|     { | ||||
|         $lazyDouble->addInterface('222')->shouldBeCalled(); | ||||
|  | ||||
|         $this->willImplement('222'); | ||||
|     } | ||||
|  | ||||
|     function it_sets_constructor_arguments_during_willBeConstructedWith_call($lazyDouble) | ||||
|     { | ||||
|         $lazyDouble->setArguments(array(1, 2, 5))->shouldBeCalled(); | ||||
|  | ||||
|         $this->willBeConstructedWith(array(1, 2, 5)); | ||||
|     } | ||||
|  | ||||
|     function it_does_not_have_method_prophecies_by_default() | ||||
|     { | ||||
|         $this->getMethodProphecies()->shouldHaveCount(0); | ||||
|     } | ||||
|  | ||||
|     /** | ||||
|      * @param \Prophecy\Prophecy\MethodProphecy    $method1 | ||||
|      * @param \Prophecy\Prophecy\MethodProphecy    $method2 | ||||
|      * @param \Prophecy\Argument\ArgumentsWildcard $arguments | ||||
|      */ | ||||
|     function it_should_get_method_prophecies_by_method_name($method1, $method2, $arguments) | ||||
|     { | ||||
|         $method1->getMethodName()->willReturn('getName'); | ||||
|         $method1->getArgumentsWildcard()->willReturn($arguments); | ||||
|         $method2->getMethodName()->willReturn('setName'); | ||||
|         $method2->getArgumentsWildcard()->willReturn($arguments); | ||||
|  | ||||
|         $this->addMethodProphecy($method1); | ||||
|         $this->addMethodProphecy($method2); | ||||
|  | ||||
|         $methods = $this->getMethodProphecies('setName'); | ||||
|         $methods->shouldHaveCount(1); | ||||
|         $methods[0]->getMethodName()->shouldReturn('setName'); | ||||
|     } | ||||
|  | ||||
|     function it_should_return_empty_array_if_no_method_prophecies_found() | ||||
|     { | ||||
|         $methods = $this->getMethodProphecies('setName'); | ||||
|         $methods->shouldHaveCount(0); | ||||
|     } | ||||
|  | ||||
|     /** | ||||
|      * @param \Prophecy\Call\CallCenter $callCenter | ||||
|      */ | ||||
|     function it_should_proxy_makeProphecyMethodCall_to_CallCenter($lazyDouble, $callCenter) | ||||
|     { | ||||
|         $this->beConstructedWith($lazyDouble, $callCenter); | ||||
|  | ||||
|         $callCenter->makeCall($this->getWrappedObject(), 'setName', array('everzet'))->willReturn(42); | ||||
|  | ||||
|         $this->makeProphecyMethodCall('setName', array('everzet'))->shouldReturn(42); | ||||
|     } | ||||
|  | ||||
|     /** | ||||
|      * @param \Prophecy\Call\CallCenter            $callCenter | ||||
|      * @param \Prophecy\Prophecy\RevealerInterface $revealer | ||||
|      */ | ||||
|     function it_should_reveal_arguments_and_return_values_from_callCenter( | ||||
|         $lazyDouble, $callCenter, $revealer | ||||
|     ) | ||||
|     { | ||||
|         $this->beConstructedWith($lazyDouble, $callCenter, $revealer); | ||||
|  | ||||
|         $revealer->reveal(array('question'))->willReturn(array('life')); | ||||
|         $revealer->reveal('answer')->willReturn(42); | ||||
|  | ||||
|         $callCenter->makeCall($this->getWrappedObject(), 'setName', array('life'))->willReturn('answer'); | ||||
|  | ||||
|         $this->makeProphecyMethodCall('setName', array('question'))->shouldReturn(42); | ||||
|     } | ||||
|  | ||||
|     /** | ||||
|      * @param \Prophecy\Call\CallCenter            $callCenter | ||||
|      * @param \Prophecy\Argument\ArgumentsWildcard $wildcard | ||||
|      * @param \Prophecy\Call\Call                  $call | ||||
|      */ | ||||
|     function it_should_proxy_getProphecyMethodCalls_to_CallCenter( | ||||
|         $lazyDouble, $callCenter, $wildcard, $call | ||||
|     ) | ||||
|     { | ||||
|         $this->beConstructedWith($lazyDouble, $callCenter); | ||||
|  | ||||
|         $callCenter->findCalls('setName', $wildcard)->willReturn(array($call)); | ||||
|  | ||||
|         $this->findProphecyMethodCalls('setName', $wildcard)->shouldReturn(array($call)); | ||||
|     } | ||||
|  | ||||
|     /** | ||||
|      * @param \Prophecy\Prophecy\MethodProphecy    $methodProphecy | ||||
|      * @param \Prophecy\Argument\ArgumentsWildcard $argumentsWildcard | ||||
|      */ | ||||
|     function its_addMethodProphecy_adds_method_prophecy( | ||||
|         $methodProphecy, $argumentsWildcard | ||||
|     ) | ||||
|     { | ||||
|         $methodProphecy->getArgumentsWildcard()->willReturn($argumentsWildcard); | ||||
|         $methodProphecy->getMethodName()->willReturn('getUsername'); | ||||
|  | ||||
|         $this->addMethodProphecy($methodProphecy); | ||||
|  | ||||
|         $this->getMethodProphecies()->shouldReturn(array( | ||||
|             'getUsername' => array($methodProphecy) | ||||
|         )); | ||||
|     } | ||||
|  | ||||
|     /** | ||||
|      * @param \Prophecy\Prophecy\MethodProphecy    $methodProphecy1 | ||||
|      * @param \Prophecy\Prophecy\MethodProphecy    $methodProphecy2 | ||||
|      * @param \Prophecy\Argument\ArgumentsWildcard $argumentsWildcard1 | ||||
|      * @param \Prophecy\Argument\ArgumentsWildcard $argumentsWildcard2 | ||||
|      */ | ||||
|     function its_addMethodProphecy_handles_prophecies_with_different_arguments( | ||||
|         $methodProphecy1, $methodProphecy2, $argumentsWildcard1, $argumentsWildcard2 | ||||
|     ) | ||||
|     { | ||||
|         $methodProphecy1->getArgumentsWildcard()->willReturn($argumentsWildcard1); | ||||
|         $methodProphecy1->getMethodName()->willReturn('getUsername'); | ||||
|  | ||||
|         $methodProphecy2->getArgumentsWildcard()->willReturn($argumentsWildcard2); | ||||
|         $methodProphecy2->getMethodName()->willReturn('getUsername'); | ||||
|  | ||||
|         $this->addMethodProphecy($methodProphecy1); | ||||
|         $this->addMethodProphecy($methodProphecy2); | ||||
|  | ||||
|         $this->getMethodProphecies()->shouldReturn(array( | ||||
|             'getUsername' => array( | ||||
|                 $methodProphecy1, | ||||
|                 $methodProphecy2, | ||||
|             ) | ||||
|         )); | ||||
|     } | ||||
|  | ||||
|     /** | ||||
|      * @param \Prophecy\Prophecy\MethodProphecy    $methodProphecy1 | ||||
|      * @param \Prophecy\Prophecy\MethodProphecy    $methodProphecy2 | ||||
|      * @param \Prophecy\Argument\ArgumentsWildcard $argumentsWildcard1 | ||||
|      * @param \Prophecy\Argument\ArgumentsWildcard $argumentsWildcard2 | ||||
|      */ | ||||
|     function its_addMethodProphecy_handles_prophecies_for_different_methods( | ||||
|         $methodProphecy1, $methodProphecy2, $argumentsWildcard1, $argumentsWildcard2 | ||||
|     ) | ||||
|     { | ||||
|         $methodProphecy1->getArgumentsWildcard()->willReturn($argumentsWildcard1); | ||||
|         $methodProphecy1->getMethodName()->willReturn('getUsername'); | ||||
|  | ||||
|         $methodProphecy2->getArgumentsWildcard()->willReturn($argumentsWildcard2); | ||||
|         $methodProphecy2->getMethodName()->willReturn('isUsername'); | ||||
|  | ||||
|         $this->addMethodProphecy($methodProphecy1); | ||||
|         $this->addMethodProphecy($methodProphecy2); | ||||
|  | ||||
|         $this->getMethodProphecies()->shouldReturn(array( | ||||
|             'getUsername' => array( | ||||
|                 $methodProphecy1 | ||||
|             ), | ||||
|             'isUsername' => array( | ||||
|                 $methodProphecy2 | ||||
|             ) | ||||
|         )); | ||||
|     } | ||||
|  | ||||
|     /** | ||||
|      * @param \Prophecy\Prophecy\MethodProphecy $methodProphecy | ||||
|      */ | ||||
|     function its_addMethodProphecy_throws_exception_when_method_has_no_ArgumentsWildcard( | ||||
|         $methodProphecy | ||||
|     ) | ||||
|     { | ||||
|         $methodProphecy->getArgumentsWildcard()->willReturn(null); | ||||
|         $methodProphecy->getObjectProphecy()->willReturn($this); | ||||
|         $methodProphecy->getMethodName()->willReturn('getTitle'); | ||||
|  | ||||
|         $this->shouldThrow('Prophecy\Exception\Prophecy\MethodProphecyException')->duringAddMethodProphecy( | ||||
|             $methodProphecy | ||||
|         ); | ||||
|     } | ||||
|  | ||||
|     function it_returns_null_after_checkPredictions_call_if_there_is_no_method_prophecies() | ||||
|     { | ||||
|         $this->checkProphecyMethodsPredictions()->shouldReturn(null); | ||||
|     } | ||||
|  | ||||
|     /** | ||||
|      * @param \Prophecy\Prophecy\MethodProphecy    $methodProphecy1 | ||||
|      * @param \Prophecy\Prophecy\MethodProphecy    $methodProphecy2 | ||||
|      * @param \Prophecy\Argument\ArgumentsWildcard $argumentsWildcard1 | ||||
|      * @param \Prophecy\Argument\ArgumentsWildcard $argumentsWildcard2 | ||||
|      */ | ||||
|     function it_throws_AggregateException_during_checkPredictions_if_predictions_fail( | ||||
|         $methodProphecy1, $methodProphecy2, $argumentsWildcard1, $argumentsWildcard2 | ||||
|     ) | ||||
|     { | ||||
|         $methodProphecy1->getMethodName()->willReturn('getName'); | ||||
|         $methodProphecy1->getArgumentsWildcard()->willReturn($argumentsWildcard1); | ||||
|         $methodProphecy1->checkPrediction() | ||||
|             ->willThrow('Prophecy\Exception\Prediction\AggregateException'); | ||||
|  | ||||
|         $methodProphecy2->getMethodName()->willReturn('setName'); | ||||
|         $methodProphecy2->getArgumentsWildcard()->willReturn($argumentsWildcard2); | ||||
|         $methodProphecy2->checkPrediction() | ||||
|             ->willThrow('Prophecy\Exception\Prediction\AggregateException'); | ||||
|  | ||||
|         $this->addMethodProphecy($methodProphecy1); | ||||
|         $this->addMethodProphecy($methodProphecy2); | ||||
|  | ||||
|         $this->shouldThrow('Prophecy\Exception\Prediction\AggregateException') | ||||
|             ->duringCheckProphecyMethodsPredictions(); | ||||
|     } | ||||
|  | ||||
|     /** | ||||
|      * @param \Prophecy\Doubler\Doubler                   $doubler | ||||
|      * @param \Prophecy\Prophecy\ProphecySubjectInterface $reflection | ||||
|      */ | ||||
|     function it_returns_new_MethodProphecy_instance_for_arbitrary_call($doubler, $reflection) | ||||
|     { | ||||
|         $doubler->double(Argument::any())->willReturn($reflection); | ||||
|  | ||||
|         $return = $this->getProphecy(); | ||||
|         $return->shouldBeAnInstanceOf('Prophecy\Prophecy\MethodProphecy'); | ||||
|         $return->getMethodName()->shouldReturn('getProphecy'); | ||||
|     } | ||||
|  | ||||
|     /** | ||||
|      * @param \Prophecy\Doubler\Doubler                   $doubler | ||||
|      * @param \Prophecy\Prophecy\ProphecySubjectInterface $reflection | ||||
|      */ | ||||
|     function it_returns_same_MethodProphecy_for_same_registered_signature($doubler, $reflection) | ||||
|     { | ||||
|         $doubler->double(Argument::any())->willReturn($reflection); | ||||
|  | ||||
|         $this->addMethodProphecy($methodProphecy1 = $this->getProphecy(1, 2, 3)); | ||||
|         $methodProphecy2 = $this->getProphecy(1, 2, 3); | ||||
|  | ||||
|         $methodProphecy2->shouldBe($methodProphecy1); | ||||
|     } | ||||
|  | ||||
|     /** | ||||
|      * @param \Prophecy\Doubler\Doubler                   $doubler | ||||
|      * @param \Prophecy\Prophecy\ProphecySubjectInterface $reflection | ||||
|      */ | ||||
|     function it_returns_new_MethodProphecy_for_different_signatures($doubler, $reflection) | ||||
|     { | ||||
|         $doubler->double(Argument::any())->willReturn($reflection); | ||||
|  | ||||
|         $value = new ObjectProphecySpecFixtureB('ABC'); | ||||
|         $value2 = new ObjectProphecySpecFixtureB('CBA'); | ||||
|  | ||||
|         $this->addMethodProphecy($methodProphecy1 = $this->getProphecy(1, 2, 3, $value)); | ||||
|         $methodProphecy2 = $this->getProphecy(1, 2, 3, $value2); | ||||
|  | ||||
|         $methodProphecy2->shouldNotBe($methodProphecy1); | ||||
|     } | ||||
|  | ||||
|     /** | ||||
|      * @param \Prophecy\Doubler\Doubler                   $doubler | ||||
|      * @param \Prophecy\Prophecy\ProphecySubjectInterface $reflection | ||||
|      */ | ||||
|     function it_returns_new_MethodProphecy_for_all_callback_signatures($doubler, $reflection) | ||||
|     { | ||||
|         $doubler->double(Argument::any())->willReturn($reflection); | ||||
|  | ||||
|         $this->addMethodProphecy($methodProphecy1 = $this->getProphecy(function(){})); | ||||
|         $methodProphecy2 = $this->getProphecy(function(){}); | ||||
|  | ||||
|         $methodProphecy2->shouldNotBe($methodProphecy1); | ||||
|     } | ||||
| } | ||||
|  | ||||
| class ObjectProphecySpecFixtureA | ||||
| { | ||||
| 	public $errors; | ||||
| } | ||||
|  | ||||
| class ObjectProphecySpecFixtureB extends ObjectProphecySpecFixtureA | ||||
| { | ||||
|     public $errors; | ||||
|     public $value = null; | ||||
|  | ||||
|     public function __construct($value) | ||||
|     { | ||||
|         $this->value = $value; | ||||
|     } | ||||
| } | ||||
| @@ -1,51 +0,0 @@ | ||||
| <?php | ||||
|  | ||||
| namespace spec\Prophecy\Prophecy; | ||||
|  | ||||
| use PhpSpec\ObjectBehavior; | ||||
|  | ||||
| class RevealerSpec extends ObjectBehavior | ||||
| { | ||||
|     function it_is_revealer() | ||||
|     { | ||||
|         $this->shouldBeAnInstanceOf('Prophecy\Prophecy\RevealerInterface'); | ||||
|     } | ||||
|  | ||||
|     /** | ||||
|      * @param \Prophecy\Prophecy\ProphecyInterface $prophecy | ||||
|      * @param \stdClass                            $object | ||||
|      */ | ||||
|     function it_reveals_single_instance_of_ProphecyInterface($prophecy, $object) | ||||
|     { | ||||
|         $prophecy->reveal()->willReturn($object); | ||||
|  | ||||
|         $this->reveal($prophecy)->shouldReturn($object); | ||||
|     } | ||||
|  | ||||
|     /** | ||||
|      * @param \Prophecy\Prophecy\ProphecyInterface $prophecy1 | ||||
|      * @param \Prophecy\Prophecy\ProphecyInterface $prophecy2 | ||||
|      * @param \stdClass                            $object1 | ||||
|      * @param \stdClass                            $object2 | ||||
|      */ | ||||
|     function it_reveals_instances_of_ProphecyInterface_inside_array( | ||||
|         $prophecy1, $prophecy2, $object1, $object2 | ||||
|     ) | ||||
|     { | ||||
|         $prophecy1->reveal()->willReturn($object1); | ||||
|         $prophecy2->reveal()->willReturn($object2); | ||||
|  | ||||
|         $this->reveal(array( | ||||
|             array('item' => $prophecy2), | ||||
|             $prophecy1 | ||||
|         ))->shouldReturn(array( | ||||
|             array('item' => $object2), | ||||
|             $object1 | ||||
|         )); | ||||
|     } | ||||
|  | ||||
|     function it_does_not_touch_non_prophecy_interface() | ||||
|     { | ||||
|         $this->reveal(42)->shouldReturn(42); | ||||
|     } | ||||
| } | ||||
| @@ -1,91 +0,0 @@ | ||||
| <?php | ||||
|  | ||||
| namespace spec\Prophecy; | ||||
|  | ||||
| use PhpSpec\ObjectBehavior; | ||||
| use Prophecy\Argument; | ||||
|  | ||||
| class ProphetSpec extends ObjectBehavior | ||||
| { | ||||
|     /** | ||||
|      * @param \Prophecy\Doubler\Doubler                   $doubler | ||||
|      * @param \Prophecy\Prophecy\ProphecySubjectInterface $double | ||||
|      */ | ||||
|     function let($doubler, $double) | ||||
|     { | ||||
|         $doubler->double(null, array())->willReturn($double); | ||||
|  | ||||
|         $this->beConstructedWith($doubler); | ||||
|     } | ||||
|  | ||||
|     function it_constructs_new_prophecy_on_prophesize_call() | ||||
|     { | ||||
|         $prophecy = $this->prophesize(); | ||||
|         $prophecy->shouldBeAnInstanceOf('Prophecy\Prophecy\ObjectProphecy'); | ||||
|     } | ||||
|  | ||||
|     /** | ||||
|      * @param \Prophecy\Prophecy\ProphecySubjectInterface $newDouble | ||||
|      */ | ||||
|     function it_constructs_new_prophecy_with_parent_class_if_specified($doubler, $newDouble) | ||||
|     { | ||||
|         $doubler->double(Argument::any(), array())->willReturn($newDouble); | ||||
|  | ||||
|         $this->prophesize('Prophecy\Prophet')->reveal()->shouldReturn($newDouble); | ||||
|     } | ||||
|  | ||||
|     /** | ||||
|      * @param \Prophecy\Prophecy\ProphecySubjectInterface $newDouble | ||||
|      */ | ||||
|     function it_constructs_new_prophecy_with_interface_if_specified($doubler, $newDouble) | ||||
|     { | ||||
|         $doubler->double(null, Argument::any())->willReturn($newDouble); | ||||
|  | ||||
|         $this->prophesize('ArrayAccess')->reveal()->shouldReturn($newDouble); | ||||
|     } | ||||
|  | ||||
|     function it_exposes_all_created_prophecies_through_getter() | ||||
|     { | ||||
|         $prophecy1 = $this->prophesize(); | ||||
|         $prophecy2 = $this->prophesize(); | ||||
|  | ||||
|         $this->getProphecies()->shouldReturn(array($prophecy1, $prophecy2)); | ||||
|     } | ||||
|  | ||||
|     function it_does_nothing_during_checkPredictions_call_if_no_predictions_defined() | ||||
|     { | ||||
|         $this->checkPredictions()->shouldReturn(null); | ||||
|     } | ||||
|  | ||||
|     /** | ||||
|      * @param \Prophecy\Prophecy\MethodProphecy    $method1 | ||||
|      * @param \Prophecy\Prophecy\MethodProphecy    $method2 | ||||
|      * @param \Prophecy\Argument\ArgumentsWildcard $arguments1 | ||||
|      * @param \Prophecy\Argument\ArgumentsWildcard $arguments2 | ||||
|      */ | ||||
|     function it_throws_AggregateException_if_defined_predictions_fail( | ||||
|         $method1, $method2, $arguments1, $arguments2 | ||||
|     ) | ||||
|     { | ||||
|         $method1->getMethodName()->willReturn('getName'); | ||||
|         $method1->getArgumentsWildcard()->willReturn($arguments1); | ||||
|         $method1->checkPrediction()->willReturn(null); | ||||
|  | ||||
|         $method2->getMethodName()->willReturn('isSet'); | ||||
|         $method2->getArgumentsWildcard()->willReturn($arguments2); | ||||
|         $method2->checkPrediction()->willThrow( | ||||
|             'Prophecy\Exception\Prediction\AggregateException' | ||||
|         ); | ||||
|  | ||||
|         $this->prophesize()->addMethodProphecy($method1); | ||||
|         $this->prophesize()->addMethodProphecy($method2); | ||||
|  | ||||
|         $this->shouldThrow('Prophecy\Exception\Prediction\AggregateException') | ||||
|             ->duringCheckPredictions(); | ||||
|     } | ||||
|  | ||||
|     function it_exposes_doubler_through_getter($doubler) | ||||
|     { | ||||
|         $this->getDoubler()->shouldReturn($doubler); | ||||
|     } | ||||
| } | ||||
| @@ -1,97 +0,0 @@ | ||||
| <?php | ||||
|  | ||||
| namespace spec\Prophecy\Util; | ||||
|  | ||||
| use PhpSpec\ObjectBehavior; | ||||
|  | ||||
| class StringUtilSpec extends ObjectBehavior | ||||
| { | ||||
|     function it_generates_proper_string_representation_for_integer() | ||||
|     { | ||||
|         $this->stringify(42)->shouldReturn('42'); | ||||
|     } | ||||
|  | ||||
|     function it_generates_proper_string_representation_for_string() | ||||
|     { | ||||
|         $this->stringify('some string')->shouldReturn('"some string"'); | ||||
|     } | ||||
|  | ||||
|     function it_generates_single_line_representation_for_multiline_string() | ||||
|     { | ||||
|         $this->stringify("some\nstring")->shouldReturn('"some\\nstring"'); | ||||
|     } | ||||
|  | ||||
|     function it_generates_proper_string_representation_for_double() | ||||
|     { | ||||
|         $this->stringify(42.3)->shouldReturn('42.3'); | ||||
|     } | ||||
|  | ||||
|     function it_generates_proper_string_representation_for_boolean_true() | ||||
|     { | ||||
|         $this->stringify(true)->shouldReturn('true'); | ||||
|     } | ||||
|  | ||||
|     function it_generates_proper_string_representation_for_boolean_false() | ||||
|     { | ||||
|         $this->stringify(false)->shouldReturn('false'); | ||||
|     } | ||||
|  | ||||
|     function it_generates_proper_string_representation_for_null() | ||||
|     { | ||||
|         $this->stringify(null)->shouldReturn('null'); | ||||
|     } | ||||
|  | ||||
|     function it_generates_proper_string_representation_for_empty_array() | ||||
|     { | ||||
|         $this->stringify(array())->shouldReturn('[]'); | ||||
|     } | ||||
|  | ||||
|     function it_generates_proper_string_representation_for_array() | ||||
|     { | ||||
|         $this->stringify(array('zet', 42))->shouldReturn('["zet", 42]'); | ||||
|     } | ||||
|  | ||||
|     function it_generates_proper_string_representation_for_hash_containing_one_value() | ||||
|     { | ||||
|         $this->stringify(array('ever' => 'zet'))->shouldReturn('["ever" => "zet"]'); | ||||
|     } | ||||
|  | ||||
|     function it_generates_proper_string_representation_for_hash() | ||||
|     { | ||||
|         $this->stringify(array('ever' => 'zet', 52 => 'hey', 'num' => 42))->shouldReturn( | ||||
|             '["ever" => "zet", 52 => "hey", "num" => 42]' | ||||
|         ); | ||||
|     } | ||||
|  | ||||
|     function it_generates_proper_string_representation_for_resource() | ||||
|     { | ||||
|         $resource = fopen(__FILE__, 'r'); | ||||
|         $this->stringify($resource)->shouldReturn('stream:'.$resource); | ||||
|     } | ||||
|  | ||||
|     /** | ||||
|      * @param \stdClass $object | ||||
|      */ | ||||
|     function it_generates_proper_string_representation_for_object($object) | ||||
|     { | ||||
|         $objHash = sprintf('%s:%s', | ||||
|             get_class($object->getWrappedObject()), | ||||
|             spl_object_hash($object->getWrappedObject()) | ||||
|         ) . " Object (\n    'objectProphecy' => Prophecy\Prophecy\ObjectProphecy Object (*Prophecy*)\n)"; | ||||
|  | ||||
|         $this->stringify($object)->shouldReturn("$objHash"); | ||||
|     } | ||||
|  | ||||
|     /** | ||||
|      * @param stdClass $object | ||||
|      */ | ||||
|     function it_generates_proper_string_representation_for_object_without_exporting($object) | ||||
|     { | ||||
|         $objHash = sprintf('%s:%s', | ||||
|             get_class($object->getWrappedObject()), | ||||
|             spl_object_hash($object->getWrappedObject()) | ||||
|         ); | ||||
|  | ||||
|         $this->stringify($object, false)->shouldReturn("$objHash"); | ||||
|     } | ||||
| } | ||||
							
								
								
									
										198
									
								
								vendor/phpspec/prophecy/src/Prophecy/Argument.php
									
									
									
									
										vendored
									
									
								
							
							
						
						
									
										198
									
								
								vendor/phpspec/prophecy/src/Prophecy/Argument.php
									
									
									
									
										vendored
									
									
								
							| @@ -1,198 +0,0 @@ | ||||
| <?php | ||||
|  | ||||
| /* | ||||
|  * This file is part of the Prophecy. | ||||
|  * (c) Konstantin Kudryashov <ever.zet@gmail.com> | ||||
|  *     Marcello Duarte <marcello.duarte@gmail.com> | ||||
|  * | ||||
|  * For the full copyright and license information, please view the LICENSE | ||||
|  * file that was distributed with this source code. | ||||
|  */ | ||||
|  | ||||
| namespace Prophecy; | ||||
|  | ||||
| use Prophecy\Argument\Token; | ||||
|  | ||||
| /** | ||||
|  * Argument tokens shortcuts. | ||||
|  * | ||||
|  * @author Konstantin Kudryashov <ever.zet@gmail.com> | ||||
|  */ | ||||
| class Argument | ||||
| { | ||||
|     /** | ||||
|      * Checks that argument is exact value or object. | ||||
|      * | ||||
|      * @param mixed $value | ||||
|      * | ||||
|      * @return Token\ExactValueToken | ||||
|      */ | ||||
|     public static function exact($value) | ||||
|     { | ||||
|         return new Token\ExactValueToken($value); | ||||
|     } | ||||
|  | ||||
|     /** | ||||
|      * Checks that argument is of specific type or instance of specific class. | ||||
|      * | ||||
|      * @param string $type Type name (`integer`, `string`) or full class name | ||||
|      * | ||||
|      * @return Token\TypeToken | ||||
|      */ | ||||
|     public static function type($type) | ||||
|     { | ||||
|         return new Token\TypeToken($type); | ||||
|     } | ||||
|  | ||||
|     /** | ||||
|      * Checks that argument object has specific state. | ||||
|      * | ||||
|      * @param string $methodName | ||||
|      * @param mixed  $value | ||||
|      * | ||||
|      * @return Token\ObjectStateToken | ||||
|      */ | ||||
|     public static function which($methodName, $value) | ||||
|     { | ||||
|         return new Token\ObjectStateToken($methodName, $value); | ||||
|     } | ||||
|  | ||||
|     /** | ||||
|      * Checks that argument matches provided callback. | ||||
|      * | ||||
|      * @param callable $callback | ||||
|      * | ||||
|      * @return Token\CallbackToken | ||||
|      */ | ||||
|     public static function that($callback) | ||||
|     { | ||||
|         return new Token\CallbackToken($callback); | ||||
|     } | ||||
|  | ||||
|     /** | ||||
|      * Matches any single value. | ||||
|      * | ||||
|      * @return Token\AnyValueToken | ||||
|      */ | ||||
|     public static function any() | ||||
|     { | ||||
|         return new Token\AnyValueToken; | ||||
|     } | ||||
|  | ||||
|     /** | ||||
|      * Matches all values to the rest of the signature. | ||||
|      * | ||||
|      * @return Token\AnyValuesToken | ||||
|      */ | ||||
|     public static function cetera() | ||||
|     { | ||||
|         return new Token\AnyValuesToken; | ||||
|     } | ||||
|  | ||||
|     /** | ||||
|      * Checks that argument matches all tokens | ||||
|      * | ||||
|      * @param mixed ... a list of tokens | ||||
|      * | ||||
|      * @return Token\LogicalAndToken | ||||
|      */ | ||||
|     public static function allOf() | ||||
|     { | ||||
|         return new Token\LogicalAndToken(func_get_args()); | ||||
|     } | ||||
|  | ||||
|     /** | ||||
|      * Checks that argument array or countable object has exact number of elements. | ||||
|      * | ||||
|      * @param integer $value array elements count | ||||
|      * | ||||
|      * @return Token\ArrayCountToken | ||||
|      */ | ||||
|     public static function size($value) | ||||
|     { | ||||
|         return new Token\ArrayCountToken($value); | ||||
|     } | ||||
|  | ||||
|     /** | ||||
|      * Checks that argument array contains (key, value) pair | ||||
|      * | ||||
|      * @param mixed $key   exact value or token | ||||
|      * @param mixed $value exact value or token | ||||
|      * | ||||
|      * @return Token\ArrayEntryToken | ||||
|      */ | ||||
|     public static function withEntry($key, $value) | ||||
|     { | ||||
|         return new Token\ArrayEntryToken($key, $value); | ||||
|     } | ||||
|  | ||||
|     /** | ||||
|      * Checks that arguments array entries all match value | ||||
|      * | ||||
|      * @param mixed $value | ||||
|      * | ||||
|      * @return Token\ArrayEveryEntryToken | ||||
|      */ | ||||
|     public static function withEveryEntry($value) | ||||
|     { | ||||
|         return new Token\ArrayEveryEntryToken($value); | ||||
|     } | ||||
|  | ||||
|     /** | ||||
|      * Checks that argument array contains value | ||||
|      * | ||||
|      * @param mixed $value | ||||
|      * | ||||
|      * @return Token\ArrayEntryToken | ||||
|      */ | ||||
|     public static function containing($value) | ||||
|     { | ||||
|         return new Token\ArrayEntryToken(self::any(), $value); | ||||
|     } | ||||
|  | ||||
|     /** | ||||
|      * Checks that argument array has key | ||||
|      * | ||||
|      * @param mixed $key exact value or token | ||||
|      * | ||||
|      * @return Token\ArrayEntryToken | ||||
|      */ | ||||
|     public static function withKey($key) | ||||
|     { | ||||
|         return new Token\ArrayEntryToken($key, self::any()); | ||||
|     } | ||||
|  | ||||
|     /** | ||||
|      * Checks that argument does not match the value|token. | ||||
|      * | ||||
|      * @param mixed $value either exact value or argument token | ||||
|      * | ||||
|      * @return Token\LogicalNotToken | ||||
|      */ | ||||
|     public static function not($value) | ||||
|     { | ||||
|         return new Token\LogicalNotToken($value); | ||||
|     } | ||||
|  | ||||
|     /** | ||||
|      * @param string $value | ||||
|      * | ||||
|      * @return Token\StringContainsToken | ||||
|      */ | ||||
|     public static function containingString($value) | ||||
|     { | ||||
|         return new Token\StringContainsToken($value); | ||||
|     } | ||||
|  | ||||
|     /** | ||||
|      * Checks that argument is identical value. | ||||
|      * | ||||
|      * @param mixed $value | ||||
|      * | ||||
|      * @return Token\IdenticalValueToken | ||||
|      */ | ||||
|     public static function is($value) | ||||
|     { | ||||
|         return new Token\IdenticalValueToken($value); | ||||
|     } | ||||
| } | ||||
| @@ -1,101 +0,0 @@ | ||||
| <?php | ||||
|  | ||||
| /* | ||||
|  * This file is part of the Prophecy. | ||||
|  * (c) Konstantin Kudryashov <ever.zet@gmail.com> | ||||
|  *     Marcello Duarte <marcello.duarte@gmail.com> | ||||
|  * | ||||
|  * For the full copyright and license information, please view the LICENSE | ||||
|  * file that was distributed with this source code. | ||||
|  */ | ||||
|  | ||||
| namespace Prophecy\Argument; | ||||
|  | ||||
| /** | ||||
|  * Arguments wildcarding. | ||||
|  * | ||||
|  * @author Konstantin Kudryashov <ever.zet@gmail.com> | ||||
|  */ | ||||
| class ArgumentsWildcard | ||||
| { | ||||
|     /** | ||||
|      * @var Token\TokenInterface[] | ||||
|      */ | ||||
|     private $tokens = array(); | ||||
|     private $string; | ||||
|  | ||||
|     /** | ||||
|      * Initializes wildcard. | ||||
|      * | ||||
|      * @param array $arguments Array of argument tokens or values | ||||
|      */ | ||||
|     public function __construct(array $arguments) | ||||
|     { | ||||
|         foreach ($arguments as $argument) { | ||||
|             if (!$argument instanceof Token\TokenInterface) { | ||||
|                 $argument = new Token\ExactValueToken($argument); | ||||
|             } | ||||
|  | ||||
|             $this->tokens[] = $argument; | ||||
|         } | ||||
|     } | ||||
|  | ||||
|     /** | ||||
|      * Calculates wildcard match score for provided arguments. | ||||
|      * | ||||
|      * @param array $arguments | ||||
|      * | ||||
|      * @return false|int False OR integer score (higher - better) | ||||
|      */ | ||||
|     public function scoreArguments(array $arguments) | ||||
|     { | ||||
|         if (0 == count($arguments) && 0 == count($this->tokens)) { | ||||
|             return 1; | ||||
|         } | ||||
|  | ||||
|         $arguments  = array_values($arguments); | ||||
|         $totalScore = 0; | ||||
|         foreach ($this->tokens as $i => $token) { | ||||
|             $argument = isset($arguments[$i]) ? $arguments[$i] : null; | ||||
|             if (1 >= $score = $token->scoreArgument($argument)) { | ||||
|                 return false; | ||||
|             } | ||||
|  | ||||
|             $totalScore += $score; | ||||
|  | ||||
|             if (true === $token->isLast()) { | ||||
|                 return $totalScore; | ||||
|             } | ||||
|         } | ||||
|  | ||||
|         if (count($arguments) > count($this->tokens)) { | ||||
|             return false; | ||||
|         } | ||||
|  | ||||
|         return $totalScore; | ||||
|     } | ||||
|  | ||||
|     /** | ||||
|      * Returns string representation for wildcard. | ||||
|      * | ||||
|      * @return string | ||||
|      */ | ||||
|     public function __toString() | ||||
|     { | ||||
|         if (null === $this->string) { | ||||
|             $this->string = implode(', ', array_map(function ($token) { | ||||
|                 return (string) $token; | ||||
|             }, $this->tokens)); | ||||
|         } | ||||
|  | ||||
|         return $this->string; | ||||
|     } | ||||
|  | ||||
|     /** | ||||
|      * @return array | ||||
|      */ | ||||
|     public function getTokens() | ||||
|     { | ||||
|         return $this->tokens; | ||||
|     } | ||||
| } | ||||
| @@ -1,52 +0,0 @@ | ||||
| <?php | ||||
|  | ||||
| /* | ||||
|  * This file is part of the Prophecy. | ||||
|  * (c) Konstantin Kudryashov <ever.zet@gmail.com> | ||||
|  *     Marcello Duarte <marcello.duarte@gmail.com> | ||||
|  * | ||||
|  * For the full copyright and license information, please view the LICENSE | ||||
|  * file that was distributed with this source code. | ||||
|  */ | ||||
|  | ||||
| namespace Prophecy\Argument\Token; | ||||
|  | ||||
| /** | ||||
|  * Any single value token. | ||||
|  * | ||||
|  * @author Konstantin Kudryashov <ever.zet@gmail.com> | ||||
|  */ | ||||
| class AnyValueToken implements TokenInterface | ||||
| { | ||||
|     /** | ||||
|      * Always scores 3 for any argument. | ||||
|      * | ||||
|      * @param $argument | ||||
|      * | ||||
|      * @return int | ||||
|      */ | ||||
|     public function scoreArgument($argument) | ||||
|     { | ||||
|         return 3; | ||||
|     } | ||||
|  | ||||
|     /** | ||||
|      * Returns false. | ||||
|      * | ||||
|      * @return bool | ||||
|      */ | ||||
|     public function isLast() | ||||
|     { | ||||
|         return false; | ||||
|     } | ||||
|  | ||||
|     /** | ||||
|      * Returns string representation for token. | ||||
|      * | ||||
|      * @return string | ||||
|      */ | ||||
|     public function __toString() | ||||
|     { | ||||
|         return '*'; | ||||
|     } | ||||
| } | ||||
| @@ -1,52 +0,0 @@ | ||||
| <?php | ||||
|  | ||||
| /* | ||||
|  * This file is part of the Prophecy. | ||||
|  * (c) Konstantin Kudryashov <ever.zet@gmail.com> | ||||
|  *     Marcello Duarte <marcello.duarte@gmail.com> | ||||
|  * | ||||
|  * For the full copyright and license information, please view the LICENSE | ||||
|  * file that was distributed with this source code. | ||||
|  */ | ||||
|  | ||||
| namespace Prophecy\Argument\Token; | ||||
|  | ||||
| /** | ||||
|  * Any values token. | ||||
|  * | ||||
|  * @author Konstantin Kudryashov <ever.zet@gmail.com> | ||||
|  */ | ||||
| class AnyValuesToken implements TokenInterface | ||||
| { | ||||
|     /** | ||||
|      * Always scores 2 for any argument. | ||||
|      * | ||||
|      * @param $argument | ||||
|      * | ||||
|      * @return int | ||||
|      */ | ||||
|     public function scoreArgument($argument) | ||||
|     { | ||||
|         return 2; | ||||
|     } | ||||
|  | ||||
|     /** | ||||
|      * Returns true to stop wildcard from processing other tokens. | ||||
|      * | ||||
|      * @return bool | ||||
|      */ | ||||
|     public function isLast() | ||||
|     { | ||||
|         return true; | ||||
|     } | ||||
|  | ||||
|     /** | ||||
|      * Returns string representation for token. | ||||
|      * | ||||
|      * @return string | ||||
|      */ | ||||
|     public function __toString() | ||||
|     { | ||||
|         return '* [, ...]'; | ||||
|     } | ||||
| } | ||||
| @@ -1,86 +0,0 @@ | ||||
| <?php | ||||
|  | ||||
| /* | ||||
|  * This file is part of the Prophecy. | ||||
|  * (c) Konstantin Kudryashov <ever.zet@gmail.com> | ||||
|  *     Marcello Duarte <marcello.duarte@gmail.com> | ||||
|  * | ||||
|  * For the full copyright and license information, please view the LICENSE | ||||
|  * file that was distributed with this source code. | ||||
|  */ | ||||
|  | ||||
| namespace Prophecy\Argument\Token; | ||||
|  | ||||
| /** | ||||
|  * Array elements count token. | ||||
|  * | ||||
|  * @author Boris Mikhaylov <kaguxmail@gmail.com> | ||||
|  */ | ||||
|  | ||||
| class ArrayCountToken implements TokenInterface | ||||
| { | ||||
|     private $count; | ||||
|  | ||||
|     /** | ||||
|      * @param integer $value | ||||
|      */ | ||||
|     public function __construct($value) | ||||
|     { | ||||
|         $this->count = $value; | ||||
|     } | ||||
|  | ||||
|     /** | ||||
|      * Scores 6 when argument has preset number of elements. | ||||
|      * | ||||
|      * @param $argument | ||||
|      * | ||||
|      * @return bool|int | ||||
|      */ | ||||
|     public function scoreArgument($argument) | ||||
|     { | ||||
|         return $this->isCountable($argument) && $this->hasProperCount($argument) ? 6 : false; | ||||
|     } | ||||
|  | ||||
|     /** | ||||
|      * Returns false. | ||||
|      * | ||||
|      * @return boolean | ||||
|      */ | ||||
|     public function isLast() | ||||
|     { | ||||
|         return false; | ||||
|     } | ||||
|  | ||||
|     /** | ||||
|      * Returns string representation for token. | ||||
|      * | ||||
|      * @return string | ||||
|      */ | ||||
|     public function __toString() | ||||
|     { | ||||
|         return sprintf('count(%s)', $this->count); | ||||
|     } | ||||
|  | ||||
|     /** | ||||
|      * Returns true if object is either array or instance of \Countable | ||||
|      * | ||||
|      * @param $argument | ||||
|      * @return bool | ||||
|      */ | ||||
|     private function isCountable($argument) | ||||
|     { | ||||
|         return (is_array($argument) || $argument instanceof \Countable); | ||||
|     } | ||||
|  | ||||
|     /** | ||||
|      * Returns true if $argument has expected number of elements | ||||
|      * | ||||
|      * @param array|\Countable $argument | ||||
|      * | ||||
|      * @return bool | ||||
|      */ | ||||
|     private function hasProperCount($argument) | ||||
|     { | ||||
|         return $this->count === count($argument); | ||||
|     } | ||||
| } | ||||
| @@ -1,143 +0,0 @@ | ||||
| <?php | ||||
|  | ||||
| /* | ||||
|  * This file is part of the Prophecy. | ||||
|  * (c) Konstantin Kudryashov <ever.zet@gmail.com> | ||||
|  *     Marcello Duarte <marcello.duarte@gmail.com> | ||||
|  * | ||||
|  * For the full copyright and license information, please view the LICENSE | ||||
|  * file that was distributed with this source code. | ||||
|  */ | ||||
|  | ||||
| namespace Prophecy\Argument\Token; | ||||
|  | ||||
| use Prophecy\Exception\InvalidArgumentException; | ||||
|  | ||||
| /** | ||||
|  * Array entry token. | ||||
|  * | ||||
|  * @author Boris Mikhaylov <kaguxmail@gmail.com> | ||||
|  */ | ||||
| class ArrayEntryToken implements TokenInterface | ||||
| { | ||||
|     /** @var \Prophecy\Argument\Token\TokenInterface */ | ||||
|     private $key; | ||||
|     /** @var \Prophecy\Argument\Token\TokenInterface */ | ||||
|     private $value; | ||||
|  | ||||
|     /** | ||||
|      * @param mixed $key   exact value or token | ||||
|      * @param mixed $value exact value or token | ||||
|      */ | ||||
|     public function __construct($key, $value) | ||||
|     { | ||||
|         $this->key = $this->wrapIntoExactValueToken($key); | ||||
|         $this->value = $this->wrapIntoExactValueToken($value); | ||||
|     } | ||||
|  | ||||
|     /** | ||||
|      * Scores half of combined scores from key and value tokens for same entry. Capped at 8. | ||||
|      * If argument implements \ArrayAccess without \Traversable, then key token is restricted to ExactValueToken. | ||||
|      * | ||||
|      * @param array|\ArrayAccess|\Traversable $argument | ||||
|      * | ||||
|      * @throws \Prophecy\Exception\InvalidArgumentException | ||||
|      * @return bool|int | ||||
|      */ | ||||
|     public function scoreArgument($argument) | ||||
|     { | ||||
|         if ($argument instanceof \Traversable) { | ||||
|             $argument = iterator_to_array($argument); | ||||
|         } | ||||
|  | ||||
|         if ($argument instanceof \ArrayAccess) { | ||||
|             $argument = $this->convertArrayAccessToEntry($argument); | ||||
|         } | ||||
|  | ||||
|         if (!is_array($argument) || empty($argument)) { | ||||
|             return false; | ||||
|         } | ||||
|  | ||||
|         $keyScores = array_map(array($this->key,'scoreArgument'), array_keys($argument)); | ||||
|         $valueScores = array_map(array($this->value,'scoreArgument'), $argument); | ||||
|         $scoreEntry = function ($value, $key) { | ||||
|             return $value && $key ? min(8, ($key + $value) / 2) : false; | ||||
|         }; | ||||
|  | ||||
|         return max(array_map($scoreEntry, $valueScores, $keyScores)); | ||||
|     } | ||||
|  | ||||
|     /** | ||||
|      * Returns false. | ||||
|      * | ||||
|      * @return boolean | ||||
|      */ | ||||
|     public function isLast() | ||||
|     { | ||||
|         return false; | ||||
|     } | ||||
|  | ||||
|     /** | ||||
|      * Returns string representation for token. | ||||
|      * | ||||
|      * @return string | ||||
|      */ | ||||
|     public function __toString() | ||||
|     { | ||||
|         return sprintf('[..., %s => %s, ...]', $this->key, $this->value); | ||||
|     } | ||||
|  | ||||
|     /** | ||||
|      * Returns key | ||||
|      * | ||||
|      * @return TokenInterface | ||||
|      */ | ||||
|     public function getKey() | ||||
|     { | ||||
|         return $this->key; | ||||
|     } | ||||
|  | ||||
|     /** | ||||
|      * Returns value | ||||
|      * | ||||
|      * @return TokenInterface | ||||
|      */ | ||||
|     public function getValue() | ||||
|     { | ||||
|         return $this->value; | ||||
|     } | ||||
|  | ||||
|     /** | ||||
|      * Wraps non token $value into ExactValueToken | ||||
|      * | ||||
|      * @param $value | ||||
|      * @return TokenInterface | ||||
|      */ | ||||
|     private function wrapIntoExactValueToken($value) | ||||
|     { | ||||
|         return $value instanceof TokenInterface ? $value : new ExactValueToken($value); | ||||
|     } | ||||
|  | ||||
|     /** | ||||
|      * Converts instance of \ArrayAccess to key => value array entry | ||||
|      * | ||||
|      * @param \ArrayAccess $object | ||||
|      * | ||||
|      * @return array|null | ||||
|      * @throws \Prophecy\Exception\InvalidArgumentException | ||||
|      */ | ||||
|     private function convertArrayAccessToEntry(\ArrayAccess $object) | ||||
|     { | ||||
|         if (!$this->key instanceof ExactValueToken) { | ||||
|             throw new InvalidArgumentException(sprintf( | ||||
|                 'You can only use exact value tokens to match key of ArrayAccess object'.PHP_EOL. | ||||
|                 'But you used `%s`.', | ||||
|                 $this->key | ||||
|             )); | ||||
|         } | ||||
|  | ||||
|         $key = $this->key->getValue(); | ||||
|  | ||||
|         return $object->offsetExists($key) ? array($key => $object[$key]) : array(); | ||||
|     } | ||||
| } | ||||
| @@ -1,82 +0,0 @@ | ||||
| <?php | ||||
|  | ||||
| /* | ||||
|  * This file is part of the Prophecy. | ||||
|  * (c) Konstantin Kudryashov <ever.zet@gmail.com> | ||||
|  *     Marcello Duarte <marcello.duarte@gmail.com> | ||||
|  * | ||||
|  * For the full copyright and license information, please view the LICENSE | ||||
|  * file that was distributed with this source code. | ||||
|  */ | ||||
|  | ||||
| namespace Prophecy\Argument\Token; | ||||
|  | ||||
| /** | ||||
|  * Array every entry token. | ||||
|  * | ||||
|  * @author Adrien Brault <adrien.brault@gmail.com> | ||||
|  */ | ||||
| class ArrayEveryEntryToken implements TokenInterface | ||||
| { | ||||
|     /** | ||||
|      * @var TokenInterface | ||||
|      */ | ||||
|     private $value; | ||||
|  | ||||
|     /** | ||||
|      * @param mixed $value exact value or token | ||||
|      */ | ||||
|     public function __construct($value) | ||||
|     { | ||||
|         if (!$value instanceof TokenInterface) { | ||||
|             $value = new ExactValueToken($value); | ||||
|         } | ||||
|  | ||||
|         $this->value = $value; | ||||
|     } | ||||
|  | ||||
|     /** | ||||
|      * {@inheritdoc} | ||||
|      */ | ||||
|     public function scoreArgument($argument) | ||||
|     { | ||||
|         if (!$argument instanceof \Traversable && !is_array($argument)) { | ||||
|             return false; | ||||
|         } | ||||
|  | ||||
|         $scores = array(); | ||||
|         foreach ($argument as $key => $argumentEntry) { | ||||
|             $scores[] = $this->value->scoreArgument($argumentEntry); | ||||
|         } | ||||
|  | ||||
|         if (empty($scores) || in_array(false, $scores, true)) { | ||||
|             return false; | ||||
|         } | ||||
|  | ||||
|         return array_sum($scores) / count($scores); | ||||
|     } | ||||
|  | ||||
|     /** | ||||
|      * {@inheritdoc} | ||||
|      */ | ||||
|     public function isLast() | ||||
|     { | ||||
|         return false; | ||||
|     } | ||||
|  | ||||
|     /** | ||||
|      * {@inheritdoc} | ||||
|      */ | ||||
|     public function __toString() | ||||
|     { | ||||
|         return sprintf('[%s, ..., %s]', $this->value, $this->value); | ||||
|     } | ||||
|  | ||||
|     /** | ||||
|      * @return TokenInterface | ||||
|      */ | ||||
|     public function getValue() | ||||
|     { | ||||
|         return $this->value; | ||||
|     } | ||||
| } | ||||
| @@ -1,75 +0,0 @@ | ||||
| <?php | ||||
|  | ||||
| /* | ||||
|  * This file is part of the Prophecy. | ||||
|  * (c) Konstantin Kudryashov <ever.zet@gmail.com> | ||||
|  *     Marcello Duarte <marcello.duarte@gmail.com> | ||||
|  * | ||||
|  * For the full copyright and license information, please view the LICENSE | ||||
|  * file that was distributed with this source code. | ||||
|  */ | ||||
|  | ||||
| namespace Prophecy\Argument\Token; | ||||
|  | ||||
| use Prophecy\Exception\InvalidArgumentException; | ||||
|  | ||||
| /** | ||||
|  * Callback-verified token. | ||||
|  * | ||||
|  * @author Konstantin Kudryashov <ever.zet@gmail.com> | ||||
|  */ | ||||
| class CallbackToken implements TokenInterface | ||||
| { | ||||
|     private $callback; | ||||
|  | ||||
|     /** | ||||
|      * Initializes token. | ||||
|      * | ||||
|      * @param callable $callback | ||||
|      * | ||||
|      * @throws \Prophecy\Exception\InvalidArgumentException | ||||
|      */ | ||||
|     public function __construct($callback) | ||||
|     { | ||||
|         if (!is_callable($callback)) { | ||||
|             throw new InvalidArgumentException(sprintf( | ||||
|                 'Callable expected as an argument to CallbackToken, but got %s.', | ||||
|                 gettype($callback) | ||||
|             )); | ||||
|         } | ||||
|  | ||||
|         $this->callback = $callback; | ||||
|     } | ||||
|  | ||||
|     /** | ||||
|      * Scores 7 if callback returns true, false otherwise. | ||||
|      * | ||||
|      * @param $argument | ||||
|      * | ||||
|      * @return bool|int | ||||
|      */ | ||||
|     public function scoreArgument($argument) | ||||
|     { | ||||
|         return call_user_func($this->callback, $argument) ? 7 : false; | ||||
|     } | ||||
|  | ||||
|     /** | ||||
|      * Returns false. | ||||
|      * | ||||
|      * @return bool | ||||
|      */ | ||||
|     public function isLast() | ||||
|     { | ||||
|         return false; | ||||
|     } | ||||
|  | ||||
|     /** | ||||
|      * Returns string representation for token. | ||||
|      * | ||||
|      * @return string | ||||
|      */ | ||||
|     public function __toString() | ||||
|     { | ||||
|         return 'callback()'; | ||||
|     } | ||||
| } | ||||
| @@ -1,116 +0,0 @@ | ||||
| <?php | ||||
|  | ||||
| /* | ||||
|  * This file is part of the Prophecy. | ||||
|  * (c) Konstantin Kudryashov <ever.zet@gmail.com> | ||||
|  *     Marcello Duarte <marcello.duarte@gmail.com> | ||||
|  * | ||||
|  * For the full copyright and license information, please view the LICENSE | ||||
|  * file that was distributed with this source code. | ||||
|  */ | ||||
|  | ||||
| namespace Prophecy\Argument\Token; | ||||
|  | ||||
| use SebastianBergmann\Comparator\ComparisonFailure; | ||||
| use Prophecy\Comparator\Factory as ComparatorFactory; | ||||
| use Prophecy\Util\StringUtil; | ||||
|  | ||||
| /** | ||||
|  * Exact value token. | ||||
|  * | ||||
|  * @author Konstantin Kudryashov <ever.zet@gmail.com> | ||||
|  */ | ||||
| class ExactValueToken implements TokenInterface | ||||
| { | ||||
|     private $value; | ||||
|     private $string; | ||||
|     private $util; | ||||
|     private $comparatorFactory; | ||||
|  | ||||
|     /** | ||||
|      * Initializes token. | ||||
|      * | ||||
|      * @param mixed             $value | ||||
|      * @param StringUtil        $util | ||||
|      * @param ComparatorFactory $comparatorFactory | ||||
|      */ | ||||
|     public function __construct($value, StringUtil $util = null, ComparatorFactory $comparatorFactory = null) | ||||
|     { | ||||
|         $this->value = $value; | ||||
|         $this->util  = $util ?: new StringUtil(); | ||||
|  | ||||
|         $this->comparatorFactory = $comparatorFactory ?: ComparatorFactory::getInstance(); | ||||
|     } | ||||
|  | ||||
|     /** | ||||
|      * Scores 10 if argument matches preset value. | ||||
|      * | ||||
|      * @param $argument | ||||
|      * | ||||
|      * @return bool|int | ||||
|      */ | ||||
|     public function scoreArgument($argument) | ||||
|     { | ||||
|         if (is_object($argument) && is_object($this->value)) { | ||||
|             $comparator = $this->comparatorFactory->getComparatorFor( | ||||
|                 $argument, $this->value | ||||
|             ); | ||||
|  | ||||
|             try { | ||||
|                 $comparator->assertEquals($argument, $this->value); | ||||
|                 return 10; | ||||
|             } catch (ComparisonFailure $failure) {} | ||||
|         } | ||||
|  | ||||
|         // If either one is an object it should be castable to a string | ||||
|         if (is_object($argument) xor is_object($this->value)) { | ||||
|             if (is_object($argument) && !method_exists($argument, '__toString')) { | ||||
|                 return false; | ||||
|             } | ||||
|  | ||||
|             if (is_object($this->value) && !method_exists($this->value, '__toString')) { | ||||
|                 return false; | ||||
|             } | ||||
|         } elseif (is_numeric($argument) && is_numeric($this->value)) { | ||||
|             // noop | ||||
|         } elseif (gettype($argument) !== gettype($this->value)) { | ||||
|             return false; | ||||
|         } | ||||
|  | ||||
|         return $argument == $this->value ? 10 : false; | ||||
|     } | ||||
|  | ||||
|     /** | ||||
|      * Returns preset value against which token checks arguments. | ||||
|      * | ||||
|      * @return mixed | ||||
|      */ | ||||
|     public function getValue() | ||||
|     { | ||||
|         return $this->value; | ||||
|     } | ||||
|  | ||||
|     /** | ||||
|      * Returns false. | ||||
|      * | ||||
|      * @return bool | ||||
|      */ | ||||
|     public function isLast() | ||||
|     { | ||||
|         return false; | ||||
|     } | ||||
|  | ||||
|     /** | ||||
|      * Returns string representation for token. | ||||
|      * | ||||
|      * @return string | ||||
|      */ | ||||
|     public function __toString() | ||||
|     { | ||||
|         if (null === $this->string) { | ||||
|             $this->string = sprintf('exact(%s)', $this->util->stringify($this->value)); | ||||
|         } | ||||
|  | ||||
|         return $this->string; | ||||
|     } | ||||
| } | ||||
| @@ -1,74 +0,0 @@ | ||||
| <?php | ||||
|  | ||||
| /* | ||||
|  * This file is part of the Prophecy. | ||||
|  * (c) Konstantin Kudryashov <ever.zet@gmail.com> | ||||
|  *     Marcello Duarte <marcello.duarte@gmail.com> | ||||
|  * | ||||
|  * For the full copyright and license information, please view the LICENSE | ||||
|  * file that was distributed with this source code. | ||||
|  */ | ||||
|  | ||||
| namespace Prophecy\Argument\Token; | ||||
|  | ||||
| use Prophecy\Util\StringUtil; | ||||
|  | ||||
| /** | ||||
|  * Identical value token. | ||||
|  * | ||||
|  * @author Florian Voutzinos <florian@voutzinos.com> | ||||
|  */ | ||||
| class IdenticalValueToken implements TokenInterface | ||||
| { | ||||
|     private $value; | ||||
|     private $string; | ||||
|     private $util; | ||||
|  | ||||
|     /** | ||||
|      * Initializes token. | ||||
|      * | ||||
|      * @param mixed      $value | ||||
|      * @param StringUtil $util | ||||
|      */ | ||||
|     public function __construct($value, StringUtil $util = null) | ||||
|     { | ||||
|         $this->value = $value; | ||||
|         $this->util  = $util ?: new StringUtil(); | ||||
|     } | ||||
|  | ||||
|     /** | ||||
|      * Scores 11 if argument matches preset value. | ||||
|      * | ||||
|      * @param $argument | ||||
|      * | ||||
|      * @return bool|int | ||||
|      */ | ||||
|     public function scoreArgument($argument) | ||||
|     { | ||||
|         return $argument === $this->value ? 11 : false; | ||||
|     } | ||||
|  | ||||
|     /** | ||||
|      * Returns false. | ||||
|      * | ||||
|      * @return bool | ||||
|      */ | ||||
|     public function isLast() | ||||
|     { | ||||
|         return false; | ||||
|     } | ||||
|  | ||||
|     /** | ||||
|      * Returns string representation for token. | ||||
|      * | ||||
|      * @return string | ||||
|      */ | ||||
|     public function __toString() | ||||
|     { | ||||
|         if (null === $this->string) { | ||||
|             $this->string = sprintf('identical(%s)', $this->util->stringify($this->value)); | ||||
|         } | ||||
|  | ||||
|         return $this->string; | ||||
|     } | ||||
| } | ||||
| @@ -1,80 +0,0 @@ | ||||
| <?php | ||||
|  | ||||
| /* | ||||
|  * This file is part of the Prophecy. | ||||
|  * (c) Konstantin Kudryashov <ever.zet@gmail.com> | ||||
|  *     Marcello Duarte <marcello.duarte@gmail.com> | ||||
|  * | ||||
|  * For the full copyright and license information, please view the LICENSE | ||||
|  * file that was distributed with this source code. | ||||
|  */ | ||||
|  | ||||
| namespace Prophecy\Argument\Token; | ||||
|  | ||||
| /** | ||||
|  * Logical AND token. | ||||
|  * | ||||
|  * @author Boris Mikhaylov <kaguxmail@gmail.com> | ||||
|  */ | ||||
| class LogicalAndToken implements TokenInterface | ||||
| { | ||||
|     private $tokens = array(); | ||||
|  | ||||
|     /** | ||||
|      * @param array $arguments exact values or tokens | ||||
|      */ | ||||
|     public function __construct(array $arguments) | ||||
|     { | ||||
|         foreach ($arguments as $argument) { | ||||
|             if (!$argument instanceof TokenInterface) { | ||||
|                 $argument = new ExactValueToken($argument); | ||||
|             } | ||||
|             $this->tokens[] = $argument; | ||||
|         } | ||||
|     } | ||||
|  | ||||
|     /** | ||||
|      * Scores maximum score from scores returned by tokens for this argument if all of them score. | ||||
|      * | ||||
|      * @param $argument | ||||
|      * | ||||
|      * @return bool|int | ||||
|      */ | ||||
|     public function scoreArgument($argument) | ||||
|     { | ||||
|         if (0 === count($this->tokens)) { | ||||
|             return false; | ||||
|         } | ||||
|  | ||||
|         $maxScore = 0; | ||||
|         foreach ($this->tokens as $token) { | ||||
|             $score = $token->scoreArgument($argument); | ||||
|             if (false === $score) { | ||||
|                 return false; | ||||
|             } | ||||
|             $maxScore = max($score, $maxScore); | ||||
|         } | ||||
|  | ||||
|         return $maxScore; | ||||
|     } | ||||
|  | ||||
|     /** | ||||
|      * Returns false. | ||||
|      * | ||||
|      * @return boolean | ||||
|      */ | ||||
|     public function isLast() | ||||
|     { | ||||
|         return false; | ||||
|     } | ||||
|  | ||||
|     /** | ||||
|      * Returns string representation for token. | ||||
|      * | ||||
|      * @return string | ||||
|      */ | ||||
|     public function __toString() | ||||
|     { | ||||
|         return sprintf('bool(%s)', implode(' AND ', $this->tokens)); | ||||
|     } | ||||
| } | ||||
| @@ -1,73 +0,0 @@ | ||||
| <?php | ||||
|  | ||||
| /* | ||||
|  * This file is part of the Prophecy. | ||||
|  * (c) Konstantin Kudryashov <ever.zet@gmail.com> | ||||
|  *     Marcello Duarte <marcello.duarte@gmail.com> | ||||
|  * | ||||
|  * For the full copyright and license information, please view the LICENSE | ||||
|  * file that was distributed with this source code. | ||||
|  */ | ||||
|  | ||||
| namespace Prophecy\Argument\Token; | ||||
|  | ||||
| /** | ||||
|  * Logical NOT token. | ||||
|  * | ||||
|  * @author Boris Mikhaylov <kaguxmail@gmail.com> | ||||
|  */ | ||||
| class LogicalNotToken implements TokenInterface | ||||
| { | ||||
|     /** @var \Prophecy\Argument\Token\TokenInterface  */ | ||||
|     private $token; | ||||
|  | ||||
|     /** | ||||
|      * @param mixed $value exact value or token | ||||
|      */ | ||||
|     public function __construct($value) | ||||
|     { | ||||
|         $this->token = $value instanceof TokenInterface? $value : new ExactValueToken($value); | ||||
|     } | ||||
|  | ||||
|     /** | ||||
|      * Scores 4 when preset token does not match the argument. | ||||
|      * | ||||
|      * @param $argument | ||||
|      * | ||||
|      * @return bool|int | ||||
|      */ | ||||
|     public function scoreArgument($argument) | ||||
|     { | ||||
|         return false === $this->token->scoreArgument($argument) ? 4 : false; | ||||
|     } | ||||
|  | ||||
|     /** | ||||
|      * Returns true if preset token is last. | ||||
|      * | ||||
|      * @return bool|int | ||||
|      */ | ||||
|     public function isLast() | ||||
|     { | ||||
|         return $this->token->isLast(); | ||||
|     } | ||||
|  | ||||
|     /** | ||||
|      * Returns originating token. | ||||
|      * | ||||
|      * @return TokenInterface | ||||
|      */ | ||||
|     public function getOriginatingToken() | ||||
|     { | ||||
|         return $this->token; | ||||
|     } | ||||
|  | ||||
|     /** | ||||
|      * Returns string representation for token. | ||||
|      * | ||||
|      * @return string | ||||
|      */ | ||||
|     public function __toString() | ||||
|     { | ||||
|         return sprintf('not(%s)', $this->token); | ||||
|     } | ||||
| } | ||||
| @@ -1,104 +0,0 @@ | ||||
| <?php | ||||
|  | ||||
| /* | ||||
|  * This file is part of the Prophecy. | ||||
|  * (c) Konstantin Kudryashov <ever.zet@gmail.com> | ||||
|  *     Marcello Duarte <marcello.duarte@gmail.com> | ||||
|  * | ||||
|  * For the full copyright and license information, please view the LICENSE | ||||
|  * file that was distributed with this source code. | ||||
|  */ | ||||
|  | ||||
| namespace Prophecy\Argument\Token; | ||||
|  | ||||
| use SebastianBergmann\Comparator\ComparisonFailure; | ||||
| use Prophecy\Comparator\Factory as ComparatorFactory; | ||||
| use Prophecy\Util\StringUtil; | ||||
|  | ||||
| /** | ||||
|  * Object state-checker token. | ||||
|  * | ||||
|  * @author Konstantin Kudryashov <ever.zet@gmail.com> | ||||
|  */ | ||||
| class ObjectStateToken implements TokenInterface | ||||
| { | ||||
|     private $name; | ||||
|     private $value; | ||||
|     private $util; | ||||
|     private $comparatorFactory; | ||||
|  | ||||
|     /** | ||||
|      * Initializes token. | ||||
|      * | ||||
|      * @param string            $methodName | ||||
|      * @param mixed             $value             Expected return value | ||||
|      * @param null|StringUtil   $util | ||||
|      * @param ComparatorFactory $comparatorFactory | ||||
|      */ | ||||
|     public function __construct( | ||||
|         $methodName, | ||||
|         $value, | ||||
|         StringUtil $util = null, | ||||
|         ComparatorFactory $comparatorFactory = null | ||||
|     ) { | ||||
|         $this->name  = $methodName; | ||||
|         $this->value = $value; | ||||
|         $this->util  = $util ?: new StringUtil; | ||||
|  | ||||
|         $this->comparatorFactory = $comparatorFactory ?: ComparatorFactory::getInstance(); | ||||
|     } | ||||
|  | ||||
|     /** | ||||
|      * Scores 8 if argument is an object, which method returns expected value. | ||||
|      * | ||||
|      * @param mixed $argument | ||||
|      * | ||||
|      * @return bool|int | ||||
|      */ | ||||
|     public function scoreArgument($argument) | ||||
|     { | ||||
|         if (is_object($argument) && method_exists($argument, $this->name)) { | ||||
|             $actual = call_user_func(array($argument, $this->name)); | ||||
|  | ||||
|             $comparator = $this->comparatorFactory->getComparatorFor( | ||||
|                 $actual, $this->value | ||||
|             ); | ||||
|  | ||||
|             try { | ||||
|                 $comparator->assertEquals($actual, $this->value); | ||||
|                 return 8; | ||||
|             } catch (ComparisonFailure $failure) { | ||||
|                 return false; | ||||
|             } | ||||
|         } | ||||
|  | ||||
|         if (is_object($argument) && property_exists($argument, $this->name)) { | ||||
|             return $argument->{$this->name} === $this->value ? 8 : false; | ||||
|         } | ||||
|  | ||||
|         return false; | ||||
|     } | ||||
|  | ||||
|     /** | ||||
|      * Returns false. | ||||
|      * | ||||
|      * @return bool | ||||
|      */ | ||||
|     public function isLast() | ||||
|     { | ||||
|         return false; | ||||
|     } | ||||
|  | ||||
|     /** | ||||
|      * Returns string representation for token. | ||||
|      * | ||||
|      * @return string | ||||
|      */ | ||||
|     public function __toString() | ||||
|     { | ||||
|         return sprintf('state(%s(), %s)', | ||||
|             $this->name, | ||||
|             $this->util->stringify($this->value) | ||||
|         ); | ||||
|     } | ||||
| } | ||||
| @@ -1,67 +0,0 @@ | ||||
| <?php | ||||
|  | ||||
| /* | ||||
|  * This file is part of the Prophecy. | ||||
|  * (c) Konstantin Kudryashov <ever.zet@gmail.com> | ||||
|  *     Marcello Duarte <marcello.duarte@gmail.com> | ||||
|  * | ||||
|  * For the full copyright and license information, please view the LICENSE | ||||
|  * file that was distributed with this source code. | ||||
|  */ | ||||
|  | ||||
| namespace Prophecy\Argument\Token; | ||||
|  | ||||
| /** | ||||
|  * String contains token. | ||||
|  * | ||||
|  * @author Peter Mitchell <pete@peterjmit.com> | ||||
|  */ | ||||
| class StringContainsToken implements TokenInterface | ||||
| { | ||||
|     private $value; | ||||
|  | ||||
|     /** | ||||
|      * Initializes token. | ||||
|      * | ||||
|      * @param string $value | ||||
|      */ | ||||
|     public function __construct($value) | ||||
|     { | ||||
|         $this->value = $value; | ||||
|     } | ||||
|  | ||||
|     public function scoreArgument($argument) | ||||
|     { | ||||
|         return strpos($argument, $this->value) !== false ? 6 : false; | ||||
|     } | ||||
|  | ||||
|     /** | ||||
|      * Returns preset value against which token checks arguments. | ||||
|      * | ||||
|      * @return mixed | ||||
|      */ | ||||
|     public function getValue() | ||||
|     { | ||||
|         return $this->value; | ||||
|     } | ||||
|  | ||||
|     /** | ||||
|      * Returns false. | ||||
|      * | ||||
|      * @return bool | ||||
|      */ | ||||
|     public function isLast() | ||||
|     { | ||||
|         return false; | ||||
|     } | ||||
|  | ||||
|     /** | ||||
|      * Returns string representation for token. | ||||
|      * | ||||
|      * @return string | ||||
|      */ | ||||
|     public function __toString() | ||||
|     { | ||||
|         return sprintf('contains("%s")', $this->value); | ||||
|     } | ||||
| } | ||||
| @@ -1,43 +0,0 @@ | ||||
| <?php | ||||
|  | ||||
| /* | ||||
|  * This file is part of the Prophecy. | ||||
|  * (c) Konstantin Kudryashov <ever.zet@gmail.com> | ||||
|  *     Marcello Duarte <marcello.duarte@gmail.com> | ||||
|  * | ||||
|  * For the full copyright and license information, please view the LICENSE | ||||
|  * file that was distributed with this source code. | ||||
|  */ | ||||
|  | ||||
| namespace Prophecy\Argument\Token; | ||||
|  | ||||
| /** | ||||
|  * Argument token interface. | ||||
|  * | ||||
|  * @author Konstantin Kudryashov <ever.zet@gmail.com> | ||||
|  */ | ||||
| interface TokenInterface | ||||
| { | ||||
|     /** | ||||
|      * Calculates token match score for provided argument. | ||||
|      * | ||||
|      * @param $argument | ||||
|      * | ||||
|      * @return bool|int | ||||
|      */ | ||||
|     public function scoreArgument($argument); | ||||
|  | ||||
|     /** | ||||
|      * Returns true if this token prevents check of other tokens (is last one). | ||||
|      * | ||||
|      * @return bool|int | ||||
|      */ | ||||
|     public function isLast(); | ||||
|  | ||||
|     /** | ||||
|      * Returns string representation for token. | ||||
|      * | ||||
|      * @return string | ||||
|      */ | ||||
|     public function __toString(); | ||||
| } | ||||
| @@ -1,76 +0,0 @@ | ||||
| <?php | ||||
|  | ||||
| /* | ||||
|  * This file is part of the Prophecy. | ||||
|  * (c) Konstantin Kudryashov <ever.zet@gmail.com> | ||||
|  *     Marcello Duarte <marcello.duarte@gmail.com> | ||||
|  * | ||||
|  * For the full copyright and license information, please view the LICENSE | ||||
|  * file that was distributed with this source code. | ||||
|  */ | ||||
|  | ||||
| namespace Prophecy\Argument\Token; | ||||
|  | ||||
| use Prophecy\Exception\InvalidArgumentException; | ||||
|  | ||||
| /** | ||||
|  * Value type token. | ||||
|  * | ||||
|  * @author Konstantin Kudryashov <ever.zet@gmail.com> | ||||
|  */ | ||||
| class TypeToken implements TokenInterface | ||||
| { | ||||
|     private $type; | ||||
|  | ||||
|     /** | ||||
|      * @param string $type | ||||
|      */ | ||||
|     public function __construct($type) | ||||
|     { | ||||
|         $checker = "is_{$type}"; | ||||
|         if (!function_exists($checker) && !interface_exists($type) && !class_exists($type)) { | ||||
|             throw new InvalidArgumentException(sprintf( | ||||
|                 'Type or class name expected as an argument to TypeToken, but got %s.', $type | ||||
|             )); | ||||
|         } | ||||
|  | ||||
|         $this->type = $type; | ||||
|     } | ||||
|  | ||||
|     /** | ||||
|      * Scores 5 if argument has the same type this token was constructed with. | ||||
|      * | ||||
|      * @param $argument | ||||
|      * | ||||
|      * @return bool|int | ||||
|      */ | ||||
|     public function scoreArgument($argument) | ||||
|     { | ||||
|         $checker = "is_{$this->type}"; | ||||
|         if (function_exists($checker)) { | ||||
|             return call_user_func($checker, $argument) ? 5 : false; | ||||
|         } | ||||
|  | ||||
|         return $argument instanceof $this->type ? 5 : false; | ||||
|     } | ||||
|  | ||||
|     /** | ||||
|      * Returns false. | ||||
|      * | ||||
|      * @return bool | ||||
|      */ | ||||
|     public function isLast() | ||||
|     { | ||||
|         return false; | ||||
|     } | ||||
|  | ||||
|     /** | ||||
|      * Returns string representation for token. | ||||
|      * | ||||
|      * @return string | ||||
|      */ | ||||
|     public function __toString() | ||||
|     { | ||||
|         return sprintf('type(%s)', $this->type); | ||||
|     } | ||||
| } | ||||
							
								
								
									
										127
									
								
								vendor/phpspec/prophecy/src/Prophecy/Call/Call.php
									
									
									
									
										vendored
									
									
								
							
							
						
						
									
										127
									
								
								vendor/phpspec/prophecy/src/Prophecy/Call/Call.php
									
									
									
									
										vendored
									
									
								
							| @@ -1,127 +0,0 @@ | ||||
| <?php | ||||
|  | ||||
| /* | ||||
|  * This file is part of the Prophecy. | ||||
|  * (c) Konstantin Kudryashov <ever.zet@gmail.com> | ||||
|  *     Marcello Duarte <marcello.duarte@gmail.com> | ||||
|  * | ||||
|  * For the full copyright and license information, please view the LICENSE | ||||
|  * file that was distributed with this source code. | ||||
|  */ | ||||
|  | ||||
| namespace Prophecy\Call; | ||||
|  | ||||
| use Exception; | ||||
|  | ||||
| /** | ||||
|  * Call object. | ||||
|  * | ||||
|  * @author Konstantin Kudryashov <ever.zet@gmail.com> | ||||
|  */ | ||||
| class Call | ||||
| { | ||||
|     private $methodName; | ||||
|     private $arguments; | ||||
|     private $returnValue; | ||||
|     private $exception; | ||||
|     private $file; | ||||
|     private $line; | ||||
|  | ||||
|     /** | ||||
|      * Initializes call. | ||||
|      * | ||||
|      * @param string      $methodName | ||||
|      * @param array       $arguments | ||||
|      * @param mixed       $returnValue | ||||
|      * @param Exception   $exception | ||||
|      * @param null|string $file | ||||
|      * @param null|int    $line | ||||
|      */ | ||||
|     public function __construct($methodName, array $arguments, $returnValue, | ||||
|                                 Exception $exception = null, $file, $line) | ||||
|     { | ||||
|         $this->methodName  = $methodName; | ||||
|         $this->arguments   = $arguments; | ||||
|         $this->returnValue = $returnValue; | ||||
|         $this->exception   = $exception; | ||||
|  | ||||
|         if ($file) { | ||||
|             $this->file = $file; | ||||
|             $this->line = intval($line); | ||||
|         } | ||||
|     } | ||||
|  | ||||
|     /** | ||||
|      * Returns called method name. | ||||
|      * | ||||
|      * @return string | ||||
|      */ | ||||
|     public function getMethodName() | ||||
|     { | ||||
|         return $this->methodName; | ||||
|     } | ||||
|  | ||||
|     /** | ||||
|      * Returns called method arguments. | ||||
|      * | ||||
|      * @return array | ||||
|      */ | ||||
|     public function getArguments() | ||||
|     { | ||||
|         return $this->arguments; | ||||
|     } | ||||
|  | ||||
|     /** | ||||
|      * Returns called method return value. | ||||
|      * | ||||
|      * @return null|mixed | ||||
|      */ | ||||
|     public function getReturnValue() | ||||
|     { | ||||
|         return $this->returnValue; | ||||
|     } | ||||
|  | ||||
|     /** | ||||
|      * Returns exception that call thrown. | ||||
|      * | ||||
|      * @return null|Exception | ||||
|      */ | ||||
|     public function getException() | ||||
|     { | ||||
|         return $this->exception; | ||||
|     } | ||||
|  | ||||
|     /** | ||||
|      * Returns callee filename. | ||||
|      * | ||||
|      * @return string | ||||
|      */ | ||||
|     public function getFile() | ||||
|     { | ||||
|         return $this->file; | ||||
|     } | ||||
|  | ||||
|     /** | ||||
|      * Returns callee line number. | ||||
|      * | ||||
|      * @return int | ||||
|      */ | ||||
|     public function getLine() | ||||
|     { | ||||
|         return $this->line; | ||||
|     } | ||||
|  | ||||
|     /** | ||||
|      * Returns short notation for callee place. | ||||
|      * | ||||
|      * @return string | ||||
|      */ | ||||
|     public function getCallPlace() | ||||
|     { | ||||
|         if (null === $this->file) { | ||||
|             return 'unknown'; | ||||
|         } | ||||
|  | ||||
|         return sprintf('%s:%d', $this->file, $this->line); | ||||
|     } | ||||
| } | ||||
| @@ -1,152 +0,0 @@ | ||||
| <?php | ||||
|  | ||||
| /* | ||||
|  * This file is part of the Prophecy. | ||||
|  * (c) Konstantin Kudryashov <ever.zet@gmail.com> | ||||
|  *     Marcello Duarte <marcello.duarte@gmail.com> | ||||
|  * | ||||
|  * For the full copyright and license information, please view the LICENSE | ||||
|  * file that was distributed with this source code. | ||||
|  */ | ||||
|  | ||||
| namespace Prophecy\Call; | ||||
|  | ||||
| use Prophecy\Prophecy\MethodProphecy; | ||||
| use Prophecy\Prophecy\ObjectProphecy; | ||||
| use Prophecy\Argument\ArgumentsWildcard; | ||||
| use Prophecy\Util\StringUtil; | ||||
| use Prophecy\Exception\Call\UnexpectedCallException; | ||||
|  | ||||
| /** | ||||
|  * Calls receiver & manager. | ||||
|  * | ||||
|  * @author Konstantin Kudryashov <ever.zet@gmail.com> | ||||
|  */ | ||||
| class CallCenter | ||||
| { | ||||
|     private $util; | ||||
|  | ||||
|     /** | ||||
|      * @var Call[] | ||||
|      */ | ||||
|     private $recordedCalls = array(); | ||||
|  | ||||
|     /** | ||||
|      * Initializes call center. | ||||
|      * | ||||
|      * @param StringUtil $util | ||||
|      */ | ||||
|     public function __construct(StringUtil $util = null) | ||||
|     { | ||||
|         $this->util = $util ?: new StringUtil; | ||||
|     } | ||||
|  | ||||
|     /** | ||||
|      * Makes and records specific method call for object prophecy. | ||||
|      * | ||||
|      * @param ObjectProphecy $prophecy | ||||
|      * @param string         $methodName | ||||
|      * @param array          $arguments | ||||
|      * | ||||
|      * @return mixed Returns null if no promise for prophecy found or promise return value. | ||||
|      * | ||||
|      * @throws \Prophecy\Exception\Call\UnexpectedCallException If no appropriate method prophecy found | ||||
|      */ | ||||
|     public function makeCall(ObjectProphecy $prophecy, $methodName, array $arguments) | ||||
|     { | ||||
|         $backtrace = debug_backtrace(); | ||||
|  | ||||
|         $file = $line = null; | ||||
|         if (isset($backtrace[2]) && isset($backtrace[2]['file'])) { | ||||
|             $file = $backtrace[2]['file']; | ||||
|             $line = $backtrace[2]['line']; | ||||
|         } | ||||
|  | ||||
|         // If no method prophecies defined, then it's a dummy, so we'll just return null | ||||
|         if ('__destruct' === $methodName || 0 == count($prophecy->getMethodProphecies())) { | ||||
|             $this->recordedCalls[] = new Call($methodName, $arguments, null, null, $file, $line); | ||||
|  | ||||
|             return null; | ||||
|         } | ||||
|  | ||||
|         // There are method prophecies, so it's a fake/stub. Searching prophecy for this call | ||||
|         $matches = array(); | ||||
|         foreach ($prophecy->getMethodProphecies($methodName) as $methodProphecy) { | ||||
|             if (0 < $score = $methodProphecy->getArgumentsWildcard()->scoreArguments($arguments)) { | ||||
|                 $matches[] = array($score, $methodProphecy); | ||||
|             } | ||||
|         } | ||||
|  | ||||
|         // If fake/stub doesn't have method prophecy for this call - throw exception | ||||
|         if (!count($matches)) { | ||||
|             throw $this->createUnexpectedCallException($prophecy, $methodName, $arguments); | ||||
|         } | ||||
|  | ||||
|         // Sort matches by their score value | ||||
|         @usort($matches, function ($match1, $match2) { return $match2[0] - $match1[0]; }); | ||||
|  | ||||
|         // If Highest rated method prophecy has a promise - execute it or return null instead | ||||
|         $returnValue = null; | ||||
|         $exception   = null; | ||||
|         if ($promise = $matches[0][1]->getPromise()) { | ||||
|             try { | ||||
|                 $returnValue = $promise->execute($arguments, $prophecy, $matches[0][1]); | ||||
|             } catch (\Exception $e) { | ||||
|                 $exception = $e; | ||||
|             } | ||||
|         } | ||||
|  | ||||
|         $this->recordedCalls[] = new Call( | ||||
|             $methodName, $arguments, $returnValue, $exception, $file, $line | ||||
|         ); | ||||
|  | ||||
|         if (null !== $exception) { | ||||
|             throw $exception; | ||||
|         } | ||||
|  | ||||
|         return $returnValue; | ||||
|     } | ||||
|  | ||||
|     /** | ||||
|      * Searches for calls by method name & arguments wildcard. | ||||
|      * | ||||
|      * @param string            $methodName | ||||
|      * @param ArgumentsWildcard $wildcard | ||||
|      * | ||||
|      * @return Call[] | ||||
|      */ | ||||
|     public function findCalls($methodName, ArgumentsWildcard $wildcard) | ||||
|     { | ||||
|         return array_values( | ||||
|             array_filter($this->recordedCalls, function (Call $call) use ($methodName, $wildcard) { | ||||
|                 return $methodName === $call->getMethodName() | ||||
|                     && 0 < $wildcard->scoreArguments($call->getArguments()) | ||||
|                 ; | ||||
|             }) | ||||
|         ); | ||||
|     } | ||||
|  | ||||
|     private function createUnexpectedCallException(ObjectProphecy $prophecy, $methodName, | ||||
|                                                    array $arguments) | ||||
|     { | ||||
|         $classname = get_class($prophecy->reveal()); | ||||
|         $argstring = implode(', ', array_map(array($this->util, 'stringify'), $arguments)); | ||||
|         $expected  = implode("\n", array_map(function (MethodProphecy $methodProphecy) { | ||||
|             return sprintf('  - %s(%s)', | ||||
|                 $methodProphecy->getMethodName(), | ||||
|                 $methodProphecy->getArgumentsWildcard() | ||||
|             ); | ||||
|         }, call_user_func_array('array_merge', $prophecy->getMethodProphecies()))); | ||||
|  | ||||
|         return new UnexpectedCallException( | ||||
|             sprintf( | ||||
|                 "Method call:\n". | ||||
|                 "  - %s(%s)\n". | ||||
|                 "on %s was not expected, expected calls were:\n%s", | ||||
|  | ||||
|                 $methodName, $argstring, $classname, $expected | ||||
|             ), | ||||
|             $prophecy, $methodName, $arguments | ||||
|         ); | ||||
|     } | ||||
| } | ||||
| @@ -1,42 +0,0 @@ | ||||
| <?php | ||||
|  | ||||
| /* | ||||
|  * This file is part of the Prophecy. | ||||
|  * (c) Konstantin Kudryashov <ever.zet@gmail.com> | ||||
|  *     Marcello Duarte <marcello.duarte@gmail.com> | ||||
|  * | ||||
|  * For the full copyright and license information, please view the LICENSE | ||||
|  * file that was distributed with this source code. | ||||
|  */ | ||||
|  | ||||
| namespace Prophecy\Comparator; | ||||
|  | ||||
| use SebastianBergmann\Comparator\Comparator; | ||||
| use SebastianBergmann\Comparator\ComparisonFailure; | ||||
|  | ||||
| /** | ||||
|  * Closure comparator. | ||||
|  * | ||||
|  * @author Konstantin Kudryashov <ever.zet@gmail.com> | ||||
|  */ | ||||
| final class ClosureComparator extends Comparator | ||||
| { | ||||
|     public function accepts($expected, $actual) | ||||
|     { | ||||
|         return is_object($expected) && $expected instanceof \Closure | ||||
|             && is_object($actual) && $actual instanceof \Closure; | ||||
|     } | ||||
|  | ||||
|     public function assertEquals($expected, $actual, $delta = 0.0, $canonicalize = false, $ignoreCase = false) | ||||
|     { | ||||
|         throw new ComparisonFailure( | ||||
|             $expected, | ||||
|             $actual, | ||||
|             // we don't need a diff | ||||
|             '', | ||||
|             '', | ||||
|             false, | ||||
|             'all closures are born different' | ||||
|         ); | ||||
|     } | ||||
| } | ||||
| @@ -1,46 +0,0 @@ | ||||
| <?php | ||||
|  | ||||
| /* | ||||
|  * This file is part of the Prophecy. | ||||
|  * (c) Konstantin Kudryashov <ever.zet@gmail.com> | ||||
|  *     Marcello Duarte <marcello.duarte@gmail.com> | ||||
|  * | ||||
|  * For the full copyright and license information, please view the LICENSE | ||||
|  * file that was distributed with this source code. | ||||
|  */ | ||||
|  | ||||
| namespace Prophecy\Comparator; | ||||
|  | ||||
| use SebastianBergmann\Comparator\Factory as BaseFactory; | ||||
|  | ||||
| /** | ||||
|  * Prophecy comparator factory. | ||||
|  * | ||||
|  * @author Konstantin Kudryashov <ever.zet@gmail.com> | ||||
|  */ | ||||
| final class Factory extends BaseFactory | ||||
| { | ||||
|     /** | ||||
|      * @var Factory | ||||
|      */ | ||||
|     private static $instance; | ||||
|  | ||||
|     public function __construct() | ||||
|     { | ||||
|         parent::__construct(); | ||||
|  | ||||
|         $this->register(new ClosureComparator()); | ||||
|     } | ||||
|  | ||||
|     /** | ||||
|      * @return Factory | ||||
|      */ | ||||
|     public static function getInstance() | ||||
|     { | ||||
|         if (self::$instance === null) { | ||||
|             self::$instance = new Factory; | ||||
|         } | ||||
|  | ||||
|         return self::$instance; | ||||
|     } | ||||
| } | ||||
| @@ -1,68 +0,0 @@ | ||||
| <?php | ||||
|  | ||||
| /* | ||||
|  * This file is part of the Prophecy. | ||||
|  * (c) Konstantin Kudryashov <ever.zet@gmail.com> | ||||
|  *     Marcello Duarte <marcello.duarte@gmail.com> | ||||
|  * | ||||
|  * For the full copyright and license information, please view the LICENSE | ||||
|  * file that was distributed with this source code. | ||||
|  */ | ||||
|  | ||||
| namespace Prophecy\Doubler; | ||||
|  | ||||
| use ReflectionClass; | ||||
|  | ||||
| /** | ||||
|  * Cached class doubler. | ||||
|  * Prevents mirroring/creation of the same structure twice. | ||||
|  * | ||||
|  * @author Konstantin Kudryashov <ever.zet@gmail.com> | ||||
|  */ | ||||
| class CachedDoubler extends Doubler | ||||
| { | ||||
|     private $classes = array(); | ||||
|  | ||||
|     /** | ||||
|      * {@inheritdoc} | ||||
|      */ | ||||
|     public function registerClassPatch(ClassPatch\ClassPatchInterface $patch) | ||||
|     { | ||||
|         $this->classes[] = array(); | ||||
|  | ||||
|         parent::registerClassPatch($patch); | ||||
|     } | ||||
|  | ||||
|     /** | ||||
|      * {@inheritdoc} | ||||
|      */ | ||||
|     protected function createDoubleClass(ReflectionClass $class = null, array $interfaces) | ||||
|     { | ||||
|         $classId = $this->generateClassId($class, $interfaces); | ||||
|         if (isset($this->classes[$classId])) { | ||||
|             return $this->classes[$classId]; | ||||
|         } | ||||
|  | ||||
|         return $this->classes[$classId] = parent::createDoubleClass($class, $interfaces); | ||||
|     } | ||||
|  | ||||
|     /** | ||||
|      * @param ReflectionClass   $class | ||||
|      * @param ReflectionClass[] $interfaces | ||||
|      * | ||||
|      * @return string | ||||
|      */ | ||||
|     private function generateClassId(ReflectionClass $class = null, array $interfaces) | ||||
|     { | ||||
|         $parts = array(); | ||||
|         if (null !== $class) { | ||||
|             $parts[] = $class->getName(); | ||||
|         } | ||||
|         foreach ($interfaces as $interface) { | ||||
|             $parts[] = $interface->getName(); | ||||
|         } | ||||
|         sort($parts); | ||||
|  | ||||
|         return md5(implode('', $parts)); | ||||
|     } | ||||
| } | ||||
| @@ -1,48 +0,0 @@ | ||||
| <?php | ||||
|  | ||||
| /* | ||||
|  * This file is part of the Prophecy. | ||||
|  * (c) Konstantin Kudryashov <ever.zet@gmail.com> | ||||
|  *     Marcello Duarte <marcello.duarte@gmail.com> | ||||
|  * | ||||
|  * For the full copyright and license information, please view the LICENSE | ||||
|  * file that was distributed with this source code. | ||||
|  */ | ||||
|  | ||||
| namespace Prophecy\Doubler\ClassPatch; | ||||
|  | ||||
| use Prophecy\Doubler\Generator\Node\ClassNode; | ||||
|  | ||||
| /** | ||||
|  * Class patch interface. | ||||
|  * Class patches extend doubles functionality or help | ||||
|  * Prophecy to avoid some internal PHP bugs. | ||||
|  * | ||||
|  * @author Konstantin Kudryashov <ever.zet@gmail.com> | ||||
|  */ | ||||
| interface ClassPatchInterface | ||||
| { | ||||
|     /** | ||||
|      * Checks if patch supports specific class node. | ||||
|      * | ||||
|      * @param ClassNode $node | ||||
|      * | ||||
|      * @return bool | ||||
|      */ | ||||
|     public function supports(ClassNode $node); | ||||
|  | ||||
|     /** | ||||
|      * Applies patch to the specific class node. | ||||
|      * | ||||
|      * @param ClassNode $node | ||||
|      * @return void | ||||
|      */ | ||||
|     public function apply(ClassNode $node); | ||||
|  | ||||
|     /** | ||||
|      * Returns patch priority, which determines when patch will be applied. | ||||
|      * | ||||
|      * @return int Priority number (higher - earlier) | ||||
|      */ | ||||
|     public function getPriority(); | ||||
| } | ||||
| @@ -1,72 +0,0 @@ | ||||
| <?php | ||||
|  | ||||
| /* | ||||
|  * This file is part of the Prophecy. | ||||
|  * (c) Konstantin Kudryashov <ever.zet@gmail.com> | ||||
|  *     Marcello Duarte <marcello.duarte@gmail.com> | ||||
|  * | ||||
|  * For the full copyright and license information, please view the LICENSE | ||||
|  * file that was distributed with this source code. | ||||
|  */ | ||||
|  | ||||
| namespace Prophecy\Doubler\ClassPatch; | ||||
|  | ||||
| use Prophecy\Doubler\Generator\Node\ClassNode; | ||||
| use Prophecy\Doubler\Generator\Node\MethodNode; | ||||
|  | ||||
| /** | ||||
|  * Disable constructor. | ||||
|  * Makes all constructor arguments optional. | ||||
|  * | ||||
|  * @author Konstantin Kudryashov <ever.zet@gmail.com> | ||||
|  */ | ||||
| class DisableConstructorPatch implements ClassPatchInterface | ||||
| { | ||||
|     /** | ||||
|      * Checks if class has `__construct` method. | ||||
|      * | ||||
|      * @param ClassNode $node | ||||
|      * | ||||
|      * @return bool | ||||
|      */ | ||||
|     public function supports(ClassNode $node) | ||||
|     { | ||||
|         return true; | ||||
|     } | ||||
|  | ||||
|     /** | ||||
|      * Makes all class constructor arguments optional. | ||||
|      * | ||||
|      * @param ClassNode $node | ||||
|      */ | ||||
|     public function apply(ClassNode $node) | ||||
|     { | ||||
|         if (!$node->hasMethod('__construct')) { | ||||
|             $node->addMethod(new MethodNode('__construct', '')); | ||||
|  | ||||
|             return; | ||||
|         } | ||||
|  | ||||
|         $constructor = $node->getMethod('__construct'); | ||||
|         foreach ($constructor->getArguments() as $argument) { | ||||
|             $argument->setDefault(null); | ||||
|         } | ||||
|  | ||||
|         $constructor->setCode(<<<PHP | ||||
| if (0 < func_num_args()) { | ||||
|     call_user_func_array(array('parent', '__construct'), func_get_args()); | ||||
| } | ||||
| PHP | ||||
|         ); | ||||
|     } | ||||
|  | ||||
|     /** | ||||
|      * Returns patch priority, which determines when patch will be applied. | ||||
|      * | ||||
|      * @return int Priority number (higher - earlier) | ||||
|      */ | ||||
|     public function getPriority() | ||||
|     { | ||||
|         return 100; | ||||
|     } | ||||
| } | ||||
| @@ -1,63 +0,0 @@ | ||||
| <?php | ||||
|  | ||||
| /* | ||||
|  * This file is part of the Prophecy. | ||||
|  * (c) Konstantin Kudryashov <ever.zet@gmail.com> | ||||
|  *     Marcello Duarte <marcello.duarte@gmail.com> | ||||
|  * | ||||
|  * For the full copyright and license information, please view the LICENSE | ||||
|  * file that was distributed with this source code. | ||||
|  */ | ||||
|  | ||||
| namespace Prophecy\Doubler\ClassPatch; | ||||
|  | ||||
| use Prophecy\Doubler\Generator\Node\ClassNode; | ||||
|  | ||||
| /** | ||||
|  * Exception patch for HHVM to remove the stubs from special methods | ||||
|  * | ||||
|  * @author Christophe Coevoet <stof@notk.org> | ||||
|  */ | ||||
| class HhvmExceptionPatch implements ClassPatchInterface | ||||
| { | ||||
|     /** | ||||
|      * Supports exceptions on HHVM. | ||||
|      * | ||||
|      * @param ClassNode $node | ||||
|      * | ||||
|      * @return bool | ||||
|      */ | ||||
|     public function supports(ClassNode $node) | ||||
|     { | ||||
|         if (!defined('HHVM_VERSION')) { | ||||
|             return false; | ||||
|         } | ||||
|  | ||||
|         return 'Exception' === $node->getParentClass() || is_subclass_of($node->getParentClass(), 'Exception'); | ||||
|     } | ||||
|  | ||||
|     /** | ||||
|      * Removes special exception static methods from the doubled methods. | ||||
|      * | ||||
|      * @param ClassNode $node | ||||
|      * | ||||
|      * @return void | ||||
|      */ | ||||
|     public function apply(ClassNode $node) | ||||
|     { | ||||
|         if ($node->hasMethod('setTraceOptions')) { | ||||
|             $node->getMethod('setTraceOptions')->useParentCode(); | ||||
|         } | ||||
|         if ($node->hasMethod('getTraceOptions')) { | ||||
|             $node->getMethod('getTraceOptions')->useParentCode(); | ||||
|         } | ||||
|     } | ||||
|  | ||||
|     /** | ||||
|      * {@inheritdoc} | ||||
|      */ | ||||
|     public function getPriority() | ||||
|     { | ||||
|         return -50; | ||||
|     } | ||||
| } | ||||
| @@ -1,135 +0,0 @@ | ||||
| <?php | ||||
|  | ||||
| /* | ||||
|  * This file is part of the Prophecy. | ||||
|  * (c) Konstantin Kudryashov <ever.zet@gmail.com> | ||||
|  *     Marcello Duarte <marcello.duarte@gmail.com> | ||||
|  * | ||||
|  * For the full copyright and license information, please view the LICENSE | ||||
|  * file that was distributed with this source code. | ||||
|  */ | ||||
|  | ||||
| namespace Prophecy\Doubler\ClassPatch; | ||||
|  | ||||
| use Prophecy\Doubler\Generator\Node\ClassNode; | ||||
|  | ||||
| /** | ||||
|  * Remove method functionality from the double which will clash with php keywords. | ||||
|  * | ||||
|  * @author Milan Magudia <milan@magudia.com> | ||||
|  */ | ||||
| class KeywordPatch implements ClassPatchInterface | ||||
| { | ||||
|     /** | ||||
|      * Support any class | ||||
|      * | ||||
|      * @param ClassNode $node | ||||
|      * | ||||
|      * @return boolean | ||||
|      */ | ||||
|     public function supports(ClassNode $node) | ||||
|     { | ||||
|         return true; | ||||
|     } | ||||
|  | ||||
|     /** | ||||
|      * Remove methods that clash with php keywords | ||||
|      * | ||||
|      * @param ClassNode $node | ||||
|      */ | ||||
|     public function apply(ClassNode $node) | ||||
|     { | ||||
|         $methodNames = array_keys($node->getMethods()); | ||||
|         $methodsToRemove = array_intersect($methodNames, $this->getKeywords()); | ||||
|         foreach ($methodsToRemove as $methodName) { | ||||
|             $node->removeMethod($methodName); | ||||
|         } | ||||
|     } | ||||
|  | ||||
|     /** | ||||
|      * Returns patch priority, which determines when patch will be applied. | ||||
|      * | ||||
|      * @return int Priority number (higher - earlier) | ||||
|      */ | ||||
|     public function getPriority() { | ||||
|         return 49; | ||||
|     } | ||||
|  | ||||
|     /** | ||||
|      * Returns array of php keywords. | ||||
|      * | ||||
|      * @return array | ||||
|      */ | ||||
|     private function getKeywords() { | ||||
|  | ||||
|         return array( | ||||
|             '__halt_compiler', | ||||
|             'abstract', | ||||
|             'and', | ||||
|             'array', | ||||
|             'as', | ||||
|             'break', | ||||
|             'callable', | ||||
|             'case', | ||||
|             'catch', | ||||
|             'class', | ||||
|             'clone', | ||||
|             'const', | ||||
|             'continue', | ||||
|             'declare', | ||||
|             'default', | ||||
|             'die', | ||||
|             'do', | ||||
|             'echo', | ||||
|             'else', | ||||
|             'elseif', | ||||
|             'empty', | ||||
|             'enddeclare', | ||||
|             'endfor', | ||||
|             'endforeach', | ||||
|             'endif', | ||||
|             'endswitch', | ||||
|             'endwhile', | ||||
|             'eval', | ||||
|             'exit', | ||||
|             'extends', | ||||
|             'final', | ||||
|             'finally', | ||||
|             'for', | ||||
|             'foreach', | ||||
|             'function', | ||||
|             'global', | ||||
|             'goto', | ||||
|             'if', | ||||
|             'implements', | ||||
|             'include', | ||||
|             'include_once', | ||||
|             'instanceof', | ||||
|             'insteadof', | ||||
|             'interface', | ||||
|             'isset', | ||||
|             'list', | ||||
|             'namespace', | ||||
|             'new', | ||||
|             'or', | ||||
|             'print', | ||||
|             'private', | ||||
|             'protected', | ||||
|             'public', | ||||
|             'require', | ||||
|             'require_once', | ||||
|             'return', | ||||
|             'static', | ||||
|             'switch', | ||||
|             'throw', | ||||
|             'trait', | ||||
|             'try', | ||||
|             'unset', | ||||
|             'use', | ||||
|             'var', | ||||
|             'while', | ||||
|             'xor', | ||||
|             'yield', | ||||
|         ); | ||||
|     } | ||||
| } | ||||
| @@ -1,73 +0,0 @@ | ||||
| <?php | ||||
|  | ||||
| /* | ||||
|  * This file is part of the Prophecy. | ||||
|  * (c) Konstantin Kudryashov <ever.zet@gmail.com> | ||||
|  *     Marcello Duarte <marcello.duarte@gmail.com> | ||||
|  * | ||||
|  * For the full copyright and license information, please view the LICENSE | ||||
|  * file that was distributed with this source code. | ||||
|  */ | ||||
|  | ||||
| namespace Prophecy\Doubler\ClassPatch; | ||||
|  | ||||
| use phpDocumentor\Reflection\DocBlock; | ||||
| use Prophecy\Doubler\Generator\Node\ClassNode; | ||||
| use Prophecy\Doubler\Generator\Node\MethodNode; | ||||
|  | ||||
| /** | ||||
|  * Discover Magical API using "@method" PHPDoc format. | ||||
|  * | ||||
|  * @author Thomas Tourlourat <thomas@tourlourat.com> | ||||
|  */ | ||||
| class MagicCallPatch implements ClassPatchInterface | ||||
| { | ||||
|     /** | ||||
|      * Support any class | ||||
|      * | ||||
|      * @param ClassNode $node | ||||
|      * | ||||
|      * @return boolean | ||||
|      */ | ||||
|     public function supports(ClassNode $node) | ||||
|     { | ||||
|         return true; | ||||
|     } | ||||
|  | ||||
|     /** | ||||
|      * Discover Magical API | ||||
|      * | ||||
|      * @param ClassNode $node | ||||
|      */ | ||||
|     public function apply(ClassNode $node) | ||||
|     { | ||||
|         $parentClass = $node->getParentClass(); | ||||
|         $reflectionClass = new \ReflectionClass($parentClass); | ||||
|  | ||||
|         $phpdoc = new DocBlock($reflectionClass->getDocComment()); | ||||
|  | ||||
|         $tagList = $phpdoc->getTagsByName('method'); | ||||
|  | ||||
|         foreach($tagList as $tag) { | ||||
|             $methodName = $tag->getMethodName(); | ||||
|  | ||||
|             if (!$reflectionClass->hasMethod($methodName)) { | ||||
|                 $methodNode = new MethodNode($tag->getMethodName()); | ||||
|                 $methodNode->setStatic($tag->isStatic()); | ||||
|  | ||||
|                 $node->addMethod($methodNode); | ||||
|             } | ||||
|         } | ||||
|     } | ||||
|  | ||||
|     /** | ||||
|      * Returns patch priority, which determines when patch will be applied. | ||||
|      * | ||||
|      * @return integer Priority number (higher - earlier) | ||||
|      */ | ||||
|     public function getPriority() | ||||
|     { | ||||
|         return 50; | ||||
|     } | ||||
| } | ||||
|  | ||||
| @@ -1,98 +0,0 @@ | ||||
| <?php | ||||
|  | ||||
| /* | ||||
|  * This file is part of the Prophecy. | ||||
|  * (c) Konstantin Kudryashov <ever.zet@gmail.com> | ||||
|  *     Marcello Duarte <marcello.duarte@gmail.com> | ||||
|  * | ||||
|  * For the full copyright and license information, please view the LICENSE | ||||
|  * file that was distributed with this source code. | ||||
|  */ | ||||
|  | ||||
| namespace Prophecy\Doubler\ClassPatch; | ||||
|  | ||||
| use Prophecy\Doubler\Generator\Node\ClassNode; | ||||
| use Prophecy\Doubler\Generator\Node\MethodNode; | ||||
| use Prophecy\Doubler\Generator\Node\ArgumentNode; | ||||
|  | ||||
| /** | ||||
|  * Add Prophecy functionality to the double. | ||||
|  * This is a core class patch for Prophecy. | ||||
|  * | ||||
|  * @author Konstantin Kudryashov <ever.zet@gmail.com> | ||||
|  */ | ||||
| class ProphecySubjectPatch implements ClassPatchInterface | ||||
| { | ||||
|     /** | ||||
|      * Always returns true. | ||||
|      * | ||||
|      * @param ClassNode $node | ||||
|      * | ||||
|      * @return bool | ||||
|      */ | ||||
|     public function supports(ClassNode $node) | ||||
|     { | ||||
|         return true; | ||||
|     } | ||||
|  | ||||
|     /** | ||||
|      * Apply Prophecy functionality to class node. | ||||
|      * | ||||
|      * @param ClassNode $node | ||||
|      */ | ||||
|     public function apply(ClassNode $node) | ||||
|     { | ||||
|         $node->addInterface('Prophecy\Prophecy\ProphecySubjectInterface'); | ||||
|         $node->addProperty('objectProphecy', 'private'); | ||||
|  | ||||
|         foreach ($node->getMethods() as $name => $method) { | ||||
|             if ('__construct' === strtolower($name)) { | ||||
|                 continue; | ||||
|             } | ||||
|  | ||||
|             $method->setCode( | ||||
|                 'return $this->getProphecy()->makeProphecyMethodCall(__FUNCTION__, func_get_args());' | ||||
|             ); | ||||
|         } | ||||
|  | ||||
|         $prophecySetter = new MethodNode('setProphecy'); | ||||
|         $prophecyArgument = new ArgumentNode('prophecy'); | ||||
|         $prophecyArgument->setTypeHint('Prophecy\Prophecy\ProphecyInterface'); | ||||
|         $prophecySetter->addArgument($prophecyArgument); | ||||
|         $prophecySetter->setCode('$this->objectProphecy = $prophecy;'); | ||||
|  | ||||
|         $prophecyGetter = new MethodNode('getProphecy'); | ||||
|         $prophecyGetter->setCode('return $this->objectProphecy;'); | ||||
|  | ||||
|         if ($node->hasMethod('__call')) { | ||||
|             $__call = $node->getMethod('__call'); | ||||
|         } else { | ||||
|             $__call = new MethodNode('__call'); | ||||
|             $__call->addArgument(new ArgumentNode('name')); | ||||
|             $__call->addArgument(new ArgumentNode('arguments')); | ||||
|  | ||||
|             $node->addMethod($__call); | ||||
|         } | ||||
|  | ||||
|         $__call->setCode(<<<PHP | ||||
| throw new \Prophecy\Exception\Doubler\MethodNotFoundException( | ||||
|     sprintf('Method `%s::%s()` not found.', get_class(\$this), func_get_arg(0)), | ||||
|     \$this->getProphecy(), func_get_arg(0) | ||||
| ); | ||||
| PHP | ||||
|         ); | ||||
|  | ||||
|         $node->addMethod($prophecySetter); | ||||
|         $node->addMethod($prophecyGetter); | ||||
|     } | ||||
|  | ||||
|     /** | ||||
|      * Returns patch priority, which determines when patch will be applied. | ||||
|      * | ||||
|      * @return int Priority number (higher - earlier) | ||||
|      */ | ||||
|     public function getPriority() | ||||
|     { | ||||
|         return 0; | ||||
|     } | ||||
| } | ||||
| @@ -1,57 +0,0 @@ | ||||
| <?php | ||||
|  | ||||
| /* | ||||
|  * This file is part of the Prophecy. | ||||
|  * (c) Konstantin Kudryashov <ever.zet@gmail.com> | ||||
|  *     Marcello Duarte <marcello.duarte@gmail.com> | ||||
|  * | ||||
|  * For the full copyright and license information, please view the LICENSE | ||||
|  * file that was distributed with this source code. | ||||
|  */ | ||||
|  | ||||
| namespace Prophecy\Doubler\ClassPatch; | ||||
|  | ||||
| use Prophecy\Doubler\Generator\Node\ClassNode; | ||||
|  | ||||
| /** | ||||
|  * ReflectionClass::newInstance patch. | ||||
|  * Makes first argument of newInstance optional, since it works but signature is misleading | ||||
|  * | ||||
|  * @author Florian Klein <florian.klein@free.fr> | ||||
|  */ | ||||
| class ReflectionClassNewInstancePatch implements ClassPatchInterface | ||||
| { | ||||
|     /** | ||||
|      * Supports ReflectionClass | ||||
|      * | ||||
|      * @param ClassNode $node | ||||
|      * | ||||
|      * @return bool | ||||
|      */ | ||||
|     public function supports(ClassNode $node) | ||||
|     { | ||||
|         return 'ReflectionClass' === $node->getParentClass(); | ||||
|     } | ||||
|  | ||||
|     /** | ||||
|      * Updates newInstance's first argument to make it optional | ||||
|      * | ||||
|      * @param ClassNode $node | ||||
|      */ | ||||
|     public function apply(ClassNode $node) | ||||
|     { | ||||
|         foreach ($node->getMethod('newInstance')->getArguments() as $argument) { | ||||
|             $argument->setDefault(null); | ||||
|         } | ||||
|     } | ||||
|  | ||||
|     /** | ||||
|      * Returns patch priority, which determines when patch will be applied. | ||||
|      * | ||||
|      * @return int Priority number (higher = earlier) | ||||
|      */ | ||||
|     public function getPriority() | ||||
|     { | ||||
|         return 50; | ||||
|     } | ||||
| } | ||||
| @@ -1,85 +0,0 @@ | ||||
| <?php | ||||
|  | ||||
| /* | ||||
|  * This file is part of the Prophecy. | ||||
|  * (c) Konstantin Kudryashov <ever.zet@gmail.com> | ||||
|  *     Marcello Duarte <marcello.duarte@gmail.com> | ||||
|  * | ||||
|  * For the full copyright and license information, please view the LICENSE | ||||
|  * file that was distributed with this source code. | ||||
|  */ | ||||
|  | ||||
| namespace Prophecy\Doubler\ClassPatch; | ||||
|  | ||||
| use Prophecy\Doubler\Generator\Node\ClassNode; | ||||
| use Prophecy\Doubler\Generator\Node\MethodNode; | ||||
|  | ||||
| /** | ||||
|  * SplFileInfo patch. | ||||
|  * Makes SplFileInfo and derivative classes usable with Prophecy. | ||||
|  * | ||||
|  * @author Konstantin Kudryashov <ever.zet@gmail.com> | ||||
|  */ | ||||
| class SplFileInfoPatch implements ClassPatchInterface | ||||
| { | ||||
|     /** | ||||
|      * Supports everything that extends SplFileInfo. | ||||
|      * | ||||
|      * @param ClassNode $node | ||||
|      * | ||||
|      * @return bool | ||||
|      */ | ||||
|     public function supports(ClassNode $node) | ||||
|     { | ||||
|         if (null === $node->getParentClass()) { | ||||
|             return false; | ||||
|         } | ||||
|  | ||||
|         return 'SplFileInfo' === $node->getParentClass() | ||||
|             || is_subclass_of($node->getParentClass(), 'SplFileInfo') | ||||
|         ; | ||||
|     } | ||||
|  | ||||
|     /** | ||||
|      * Updated constructor code to call parent one with dummy file argument. | ||||
|      * | ||||
|      * @param ClassNode $node | ||||
|      */ | ||||
|     public function apply(ClassNode $node) | ||||
|     { | ||||
|         if ($node->hasMethod('__construct')) { | ||||
|             $constructor = $node->getMethod('__construct'); | ||||
|         } else { | ||||
|             $constructor = new MethodNode('__construct'); | ||||
|             $node->addMethod($constructor); | ||||
|         } | ||||
|  | ||||
|         if ($this->nodeIsDirectoryIterator($node)) { | ||||
|             $constructor->setCode('return parent::__construct("' . __DIR__ . '");'); | ||||
|             return; | ||||
|         } | ||||
|  | ||||
|         $constructor->useParentCode(); | ||||
|     } | ||||
|  | ||||
|     /** | ||||
|      * Returns patch priority, which determines when patch will be applied. | ||||
|      * | ||||
|      * @return int Priority number (higher - earlier) | ||||
|      */ | ||||
|     public function getPriority() | ||||
|     { | ||||
|         return 50; | ||||
|     } | ||||
|  | ||||
|     /** | ||||
|      * @param ClassNode $node | ||||
|      * @return boolean | ||||
|      */ | ||||
|     private function nodeIsDirectoryIterator(ClassNode $node) | ||||
|     { | ||||
|         $parent = $node->getParentClass(); | ||||
|         return 'DirectoryIterator' === $parent | ||||
|             || is_subclass_of($parent, 'DirectoryIterator'); | ||||
|     } | ||||
| } | ||||
| @@ -1,83 +0,0 @@ | ||||
| <?php | ||||
|  | ||||
| /* | ||||
|  * This file is part of the Prophecy. | ||||
|  * (c) Konstantin Kudryashov <ever.zet@gmail.com> | ||||
|  *     Marcello Duarte <marcello.duarte@gmail.com> | ||||
|  * | ||||
|  * For the full copyright and license information, please view the LICENSE | ||||
|  * file that was distributed with this source code. | ||||
|  */ | ||||
|  | ||||
| namespace Prophecy\Doubler\ClassPatch; | ||||
|  | ||||
| use Prophecy\Doubler\Generator\Node\ClassNode; | ||||
| use Prophecy\Doubler\Generator\Node\MethodNode; | ||||
|  | ||||
| /** | ||||
|  * Traversable interface patch. | ||||
|  * Forces classes that implement interfaces, that extend Traversable to also implement Iterator. | ||||
|  * | ||||
|  * @author Konstantin Kudryashov <ever.zet@gmail.com> | ||||
|  */ | ||||
| class TraversablePatch implements ClassPatchInterface | ||||
| { | ||||
|     /** | ||||
|      * Supports nodetree, that implement Traversable, but not Iterator or IteratorAggregate. | ||||
|      * | ||||
|      * @param ClassNode $node | ||||
|      * | ||||
|      * @return bool | ||||
|      */ | ||||
|     public function supports(ClassNode $node) | ||||
|     { | ||||
|         if (in_array('Iterator', $node->getInterfaces())) { | ||||
|             return false; | ||||
|         } | ||||
|         if (in_array('IteratorAggregate', $node->getInterfaces())) { | ||||
|             return false; | ||||
|         } | ||||
|  | ||||
|         foreach ($node->getInterfaces() as $interface) { | ||||
|             if ('Traversable' !== $interface && !is_subclass_of($interface, 'Traversable')) { | ||||
|                 continue; | ||||
|             } | ||||
|             if ('Iterator' === $interface || is_subclass_of($interface, 'Iterator')) { | ||||
|                 continue; | ||||
|             } | ||||
|             if ('IteratorAggregate' === $interface || is_subclass_of($interface, 'IteratorAggregate')) { | ||||
|                 continue; | ||||
|             } | ||||
|  | ||||
|             return true; | ||||
|         } | ||||
|  | ||||
|         return false; | ||||
|     } | ||||
|  | ||||
|     /** | ||||
|      * Forces class to implement Iterator interface. | ||||
|      * | ||||
|      * @param ClassNode $node | ||||
|      */ | ||||
|     public function apply(ClassNode $node) | ||||
|     { | ||||
|         $node->addInterface('Iterator'); | ||||
|  | ||||
|         $node->addMethod(new MethodNode('current')); | ||||
|         $node->addMethod(new MethodNode('key')); | ||||
|         $node->addMethod(new MethodNode('next')); | ||||
|         $node->addMethod(new MethodNode('rewind')); | ||||
|         $node->addMethod(new MethodNode('valid')); | ||||
|     } | ||||
|  | ||||
|     /** | ||||
|      * Returns patch priority, which determines when patch will be applied. | ||||
|      * | ||||
|      * @return int Priority number (higher - earlier) | ||||
|      */ | ||||
|     public function getPriority() | ||||
|     { | ||||
|         return 100; | ||||
|     } | ||||
| } | ||||
| @@ -1,22 +0,0 @@ | ||||
| <?php | ||||
|  | ||||
| /* | ||||
|  * This file is part of the Prophecy. | ||||
|  * (c) Konstantin Kudryashov <ever.zet@gmail.com> | ||||
|  *     Marcello Duarte <marcello.duarte@gmail.com> | ||||
|  * | ||||
|  * For the full copyright and license information, please view the LICENSE | ||||
|  * file that was distributed with this source code. | ||||
|  */ | ||||
|  | ||||
| namespace Prophecy\Doubler; | ||||
|  | ||||
| /** | ||||
|  * Core double interface. | ||||
|  * All doubled classes will implement this one. | ||||
|  * | ||||
|  * @author Konstantin Kudryashov <ever.zet@gmail.com> | ||||
|  */ | ||||
| interface DoubleInterface | ||||
| { | ||||
| } | ||||
Some files were not shown because too many files have changed in this diff Show More
		Reference in New Issue
	
	Block a user
	 sujitprasad
					sujitprasad