Skip to content

Use Doctrine Instantiator for ClassMetadata new instance creation #956

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

Merged
merged 3 commits into from
Oct 6, 2014
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
5 changes: 4 additions & 1 deletion .travis.yml
Original file line number Diff line number Diff line change
Expand Up @@ -4,10 +4,13 @@ php:
- 5.3
- 5.4
- 5.5
- 5.6

env:
- MONGO_VERSION=1.2.12
- MONGO_VERSION=1.5.1
- MONGO_VERSION=1.3.7
- MONGO_VERSION=1.4.5
- MONGO_VERSION=stable

services: mongodb

Expand Down
17 changes: 13 additions & 4 deletions CHANGELOG-1.0.md
Original file line number Diff line number Diff line change
Expand Up @@ -15,6 +15,14 @@ To generate a changelog summary since the last version, run
1.0.x-dev
---------

#### `__clone()` method no longer called when documents are instantiated via `ClassMetadata::newInstance()`

As of [#956](https://github.com/doctrine/mongodb-odm/pull/956), ClassMetadata
uses the [Doctrine Instantiator](https://github.com/doctrine/instantiator)
library to create new document instances. This library avoids calling
`__clone()` or any public API on instantiated objects. This is a BC break for\
code that may have relied upon the previous behavior.

1.0.0-BETA11 (2014-06-06)
-------------------------

Expand Down Expand Up @@ -95,10 +103,11 @@ deprecated `slaveOkay` option. Much of this work was implemented in

The `findAll()` and `findBy()` methods in DocumentRepository previously returned
a Cursor object, which was not compatible with the ObjectRepository interface in
Doctrine Common. This has been changed in #752, so these methods now return a
numerically indexed array. The change also affects the magic repository methods,
which utilize `findBy()` internally. If users require a Cursor, they should
utilize the query builder or a custom repository method.
Doctrine Common. This has been changed in
[#752](https://github.com/doctrine/mongodb-odm/pull/752), so these methods now
return a numerically indexed array. The change also affects the magic repository
methods, which utilize `findBy()` internally. If users require a Cursor, they
should utilize the query builder or a custom repository method.

#### Lifecycle callbacks and AlsoLoad

Expand Down
1 change: 1 addition & 0 deletions composer.json
Original file line number Diff line number Diff line change
Expand Up @@ -19,6 +19,7 @@
"doctrine/common": "2.4.*",
"doctrine/cache": "~1.0",
"doctrine/inflector": "~1.0",
"doctrine/instantiator": "~1.0.1",
"doctrine/mongodb": ">=1.1.5,<2.0"
},
"require-dev": {
Expand Down
17 changes: 6 additions & 11 deletions lib/Doctrine/ODM/MongoDB/Mapping/ClassMetadata.php
Original file line number Diff line number Diff line change
Expand Up @@ -19,6 +19,7 @@

namespace Doctrine\ODM\MongoDB\Mapping;

use Doctrine\Instantiator\Instantiator;
use Doctrine\ODM\MongoDB\LockException;

/**
Expand Down Expand Up @@ -49,11 +50,9 @@ class ClassMetadata extends ClassMetadataInfo
public $reflFields = array();

/**
* The prototype from which new instances of the mapped class are created.
*
* @var object
* @var \Doctrine\Instantiator\InstantiatorInterface|null
*/
private $prototype;
private $instantiator;

/**
* Initializes a new ClassMetadata instance that will hold the object-document mapping
Expand All @@ -67,6 +66,7 @@ public function __construct($documentName)
$this->reflClass = new \ReflectionClass($documentName);
$this->namespace = $this->reflClass->getNamespaceName();
$this->setCollection($this->reflClass->getShortName());
$this->instantiator = new Instantiator();
}

/**
Expand Down Expand Up @@ -176,6 +176,7 @@ public function __wakeup()
{
// Restore ReflectionClass and properties
$this->reflClass = new \ReflectionClass($this->name);
$this->instantiator = $this->instantiator ?: new Instantiator();

foreach ($this->fieldMappings as $field => $mapping) {
if (isset($mapping['declared'])) {
Expand All @@ -195,12 +196,6 @@ public function __wakeup()
*/
public function newInstance()
{
if ($this->prototype === null) {
$this->prototype = version_compare(PHP_VERSION, '5.4.0', '>=')
? $this->reflClass->newInstanceWithoutConstructor()
: unserialize(sprintf('O:%d:"%s":0:{}', strlen($this->name), $this->name));
}

return clone $this->prototype;
return $this->instantiator->instantiate($this->name);
}
}