New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
[WIP] Fix instantiation for latest PHP versions. #377
Conversation
Could you just rephrase the commit message ? the important part is not that it uses |
Sure thing. |
Test failures are related to https://bugs.php.net/bug.php?id=67453. Seems we have the same issue in PHPUnit (sebastianbergmann/phpunit-mock-objects#178). I'm unaware of any known workarounds at the moment. I'm going to close this until I have more information and more time. |
@stof do you think the dependencies here on the composer.json should be tighter to the 3rd digit so the ~ would not take us through the braks from 2.1 onwards? that i know the promise and BC compatibility applies from 2.3 onwards, so imo we should be doing this in all projects, unless is deliberate. But that is for symfony, for other libraries it should also be even more carefuly. But i could be wrong, if so please correct me @stof 🍰 |
@cordoval the Symfony constraints are not changed in this PR, so I don't really see the reason of this comment here. And given that Symfony follows semver, using the semver constraint is the best one. For the Instantiator library, I trust @Ocramius to follow semver properly as well instead of breaking BC in minor or patch releases. |
FYI, the 5.6 situation is still not clear in internals. As for semver, I'm quite serious about stability of this component. |
@Ocramius Do you have any ideas to work around https://bugs.php.net/bug.php?id=67453 in 5.4/5.5? |
Reopening this as a WIP for the fix |
@Ocramius The existing code in PhpSpec has some more logic when building the serialized string. Maybe it could help for Instantiator as well ? |
The php internals bug is exactly what is being discussed in internals
|
ocramius/instantiator
.
@Ocramius the handling of default properties of the class, in the |
@stof Seems that was deliberately removed in Ocramius/Instantiator@dcba7c6. |
@stof I actually removed all that logic in Ocramius/Instantiator@dcba7c6 - what is the specific use-case here? |
@whatthejeff too fast :-) |
PHP 5.4.29 and 5.5.13 introduced a BC break that prevents using serialization as a means for instantiating internal objects without calling their constructor (unless they implement `Serializable`) [[1]]. This issue is still evolving and workarounds are currently being discussed in the PHP internals mailing list [[2]]. In the mean time, since many PHP libraries rely on this functionality which is becoming increasingly complicated to support, @Ocramius has created [`ocramius/instantiator`](https://github.com/Ocramius/Instantiator) [[3]]. This commit adds support for `ocramius/instantiator` so that phpspec can continue to support this feature and stay in sync with other PHP libraries which support this feature without having to duplicate logic/updates across multiple projects. Please note that switching to `ocramius/instantiator` doesn't immediately solve all problems related to this BC break. Right now some of our tests are still failing. Ideally, as work arounds become available, they will be added to `ocramius/instantiator`. [1]:http://news.php.net/php.internals/74654 [2]:http://marc.info/?t=140347878100001&r=1&w=2 [3]:https://twitter.com/s_bergmann/status/475284594141691904
} | ||
|
||
return serialize(null); | ||
$instantiator = new \Instantiator\Instantiator(); |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Import this class, plus it should probably be cached locally (private property)
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Alright. It wasn't imported initially because it needs to be aliased and I wasn't feeling clever enough to think of a good alias :P
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Ah, right. Then the FQCN is fine.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
@whatthejeff if performance is not a problem here, then it's fine. It can also be left out and handled later instead.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
The instantiator already caches internally, so it's pretty ok.
@stof i meant to perhaps get feedback to open a separate ticket, it is not related. " semver constraint" what you mean by that ~2.1 vs ~2.1.0 ? even when api is not broken, added features can break sometimes the userland layer, doing it ~2.1.0 makes it safer to just include bugfixes alone. |
@cordoval if you break something in userland when addign a new feature, it means your new feature is not implemented in a backward compatible way, and so the version introducing it MUST be a major version. Otherwise, you don't follow semver |
correct but i am referring to the cases where you add a method that is being overwritten already, that breaks stuff. This is explained at the beginning of the document "For example, if we add a new method to a class, this will break an application which extended this class and added the same method, but with a different method signature." ref. http://symfony.com/doc/current/contributing/code/bc.html of course it is an edge case but honestly we have little control on userland so that is why specifying 3 digits like in nodejs and elsewhere is a better practice imo. At least in userland, not in library maintainer land. |
but we don't extend the Instantiator library. We only use it, so we are not affected by this. We have control about what we do with the library. We are the userland for this case, as it is an internal dependency, not something exposed to phpspec users |
@whatthejeff are you looking at why this is still blowing the tests for ExceptionFactory under php >= 5.4? |
@MarcelloDuarte It's mentioned earlier in this ticket. The test failures are due to https://bugs.php.net/bug.php?id=67453. According to @remicollet, the fix he committed is tentative for 5.6 and will not be ported to 5.4/5.5 [1]. Unfortunately, I don't think there's a workaround at the moment. We actually have the same issue in PHPUnit. As far as I know, the discussions on how to address this in 5.4/5.5 are still in progress. |
@MarcelloDuarte my suggestion is to merge this, which already fixes the library for some cases, even if it does not fix it everywhere. It is better than the current solution which is already broken in these cases anyway. |
So PHP 5.4.30 has been released. From what I can tell, there will no longer be a way in PHP 5.4/5.5 to instantiate internal classes that don't implement custom serializers without invoking their constructors. This means that the tests that are failing on PHP 5.4/5.5 will continue to fail. |
For reference, here is the relevant excerpt from the upgrading guide:
|
We can no longer instantiate `ArrayObject` without calling its constructor in PHP 5.4/5.5. Since we were only using it as a generic fixture, replace `ArrayObject` with `stdClass`.
The HHVM failure is a prophecy bug. Prophecy is failing because it's grabbing scalar type hints from HNI extensions. For instance: $prophet = new Prophecy\Prophet;
$prophet->prophesize('ReflectionMethod')->reveal(); will fail because it adds the scalar type hints to the export method: public static function export(string $cls, string $name, bool $ret = false) {
return $this->getProphecy()->makeProphecyMethodCall(__FUNCTION__, func_get_args());
} |
@ciaranmcnulty: It's as fixed as it's going to be. Due to security issues, certain internal objects can no longer be instantiated with the After a bit of testing, the following seem to be the only core classes that generate the 'Erroneous data format for unserializing...' message now:
|
Any news on this? |
There's still no clear resolution path from internals about PHP 5.6 :\ Marco Pivetta On Wed, Jul 16, 2014 at 2:13 PM, Sebastiaan Stok notifications@github.com
|
@whatthejeff Is this just blocked on the prophecy PR? It looks like it fixes our test suite, which is a win... |
@whatthejeff Ah, so it's merged and we're waiting on a new point release of Prophecy for this? |
FYI, I provided some fixes that give us compatibility when working with 5.5.14 and 5.4.30. 5.6.0-rc* is still unclear and depends on php/php-src#733, but if that's merged, then |
I guess we need a point release of Prophecy to point the new version to (to fix HHVM issue) and then we can merge this. @everzet any chance of getting Prophecy 1.1.1? |
Ah wait, this is already in the latest prophecy. @whatthejeff can you bump the Prophecy dependency in your branch please, to see if that fixes the HHVM failures in this PR? |
@ciaranmcnulty We probably need to update travis to test against HHVM nightly since HHVM 3 has some parity regressions in the Reflection API. |
HHVM being such a moving target seems to be problematic - I wonder at what point we have to start paying attention to testing multiple HHVM versions? |
Looks like the prophecy dependency doesn't need to be bumped. Seems there is still a remaining HHVM failure I need to look into. I should have time to investigate it in the next couple of days. |
Alright, I've confirmed that the remaining issue is indeed another Zend compatibility issue in HHVM. Here is a quick reproduce case: <?php
class TestArray extends ArrayObject
{
public function offsetExists($index)
{
return true;
}
}
$test = new TestArray();
var_dump(isset($test['abc'])); In Zend PHP you get the following:
And in HHVM you get the following:
This is related to facebook/hhvm#2181 and facebook/hhvm#2871. Basically when you use |
HHVM issue is here: facebook/hhvm#3309 |
@ciaranmcnulty The HHVM bug is fixed now. I just confirmed that all tests pass in the latest HHVM. Would you mind restarting the travis build? |
I don't have permissions for that - @MarcelloDuarte ? |
@ciaranmcnulty Are you logged in? You should be able to do a restart on travis if you're a collaborator on github. |
@whatthejeff Thanks ;-) |
@ciaranmcnulty Oh wait, I don't think you reran my test. Can you rerun this one: https://travis-ci.org/phpspec/phpspec/builds/31117450 |
Thanks, @ciaranmcnulty. All is green now \o/ |
[WIP] Fix instantiation for latest PHP versions.
Thanks for all the hard work @whatthejeff |
PHP 5.4.29 and 5.5.13 introduced a BC break that prevents using serialization as a means for instantiating internal objects without calling their constructor (unless they implement
Serializable
) [1]. This issue is still evolving and workarounds are currently being discussed in the PHP internals mailing list [2].In the mean time, since many PHP libraries rely on this functionality which is becoming increasingly complicated to support, @Ocramius has created
ocramius/instantiator
[3]. This PR adds support forocramius/instantiator
so that phpspec can continue to support this feature and stay in sync with other PHP libraries which support this feature without having to duplicate logic/updates across multiple projects.Please note that switching to
ocramius/instantiator
doesn't immediately solve all problems related to this BC break. Right now some of our tests are still failing. Ideally, as workarounds become available, they will be added toocramius/instantiator
.