DDC-842: spl_object_hash tries to get hash from array - fails #1041

Open
opened 2026-01-22 12:59:48 +01:00 by admin · 0 comments
Owner

Originally created by @doctrinebot on GitHub (Oct 19, 2010).

Jira issue originally created by user sebastian.hoitz:

I have a model which looks like this:

Class A
protected $collectionB = array(); // Holds many Class B instances
protected $collectionC = array(); // Holds many Class C instances

Class B
protected $classC; // Holds one Class C instance

Class C
protected $attributes; // Holds many attributes which are stored in another entitty with SINGLE_TABLE discriminator

When I try to persist my object to the database, Doctrine causes this error:

Message: spl*object*hash() expects parameter 1 to be object, array given
File: C:\Users\Sebastian Hoitz\Documents\Entwicklung\kt_api\trunk\library\Doctrine\ORM\UnitOfWork.php
Line: 2043
Trace:

#0 [internal function]: PHPUnit*Util_ErrorHandler::handleError(2, 'spl_object*hash...', 'C:\Users\Sebast...', 2043, Array)
#1 C:\Users\Sebastian Hoitz\Documents\Entwicklung\kt*api\trunk\library\Doctrine\ORM\UnitOfWork.php(2043): spl_object*hash(Array)
#2 C:\Users\Sebastian Hoitz\Documents\Entwicklung\kt_api\trunk\library\Doctrine\ORM\Persisters\ManyToManyPersister.php(110): Doctrine\ORM\UnitOfWork->getEntityIdentifier(Array)
#3 C:\Users\Sebastian Hoitz\Documents\Entwicklung\kt*api\trunk\library\Doctrine\ORM\Persisters\ManyToManyPersister.php(92): Doctrine\ORM\Persisters\ManyToManyPersister->*collectJoinTableColumnParameters(Object(Doctrine\ORM\PersistentCollection), Array)
#4 C:\Users\Sebastian Hoitz\Documents\Entwicklung\kt*api\trunk\library\Doctrine\ORM\Persisters\AbstractCollectionPersister.php(124): Doctrine\ORM\Persisters\ManyToManyPersister->*getInsertRowSQLParameters(Object(Doctrine\ORM\PersistentCollection), Array)
#5 C:\Users\Sebastian Hoitz\Documents\Entwicklung\kt_api\trunk\library\Doctrine\ORM\Persisters\AbstractCollectionPersister.php(104): Doctrine\ORM\Persisters\AbstractCollectionPersister->insertRows(Object(Doctrine\ORM\PersistentCollection))
#6 C:\Users\Sebastian Hoitz\Documents\Entwicklung\kt_api\trunk\library\Doctrine\ORM\UnitOfWork.php(303): Doctrine\ORM\Persisters\AbstractCollectionPersister->update(Object(Doctrine\ORM\PersistentCollection))
#7 C:\Users\Sebastian Hoitz\Documents\Entwicklung\kt_api\trunk\library\Doctrine\ORM\EntityManager.php(320): Doctrine\ORM\UnitOfWork->commit()
#8 C:\Users\Sebastian Hoitz\Documents\Entwicklung\kt_models\trunk\library\App\Model\Service\Dao\Doctrine.php(26): Doctrine\ORM\EntityManager->flush()
#9 C:\Users\Sebastian Hoitz\Documents\Entwicklung\kt*models\trunk\library\App\Model\Service\Abstract.php(54): App_Model_Service_Dao_Doctrine->save(Object(App_Model*Ticket))
#10 C:\Users\Sebastian Hoitz\Documents\Entwicklung\kt*models\trunk\library\App\Model\Abstract.php(264): App_Model_Service_Abstract->save(Object(App_Model*Ticket))
#11 C:\Users\Sebastian Hoitz\Documents\Entwicklung\kt*models\trunk\library\App\Model\Ticket.php(75): App_Model*Abstract->save()
#12 C:\Users\Sebastian Hoitz\Documents\Entwicklung\kt*api\trunk\application\controllers\TicketController.php(69): App_Model*Ticket->save()
#13 C:\Users\Sebastian Hoitz\Documents\Entwicklung\kt_api\trunk\library\Zend\Controller\Action.php(513): TicketController->putAction()
#14 C:\Users\Sebastian Hoitz\Documents\Entwicklung\kt*api\trunk\library\Zend\Controller\Dispatcher\Standard.php(295): Zend_Controller*Action->dispatch('putAction')
#15 C:\Users\Sebastian Hoitz\Documents\Entwicklung\kt*api\trunk\library\Zend\Controller\Front.php(954): Zend_Controller_Dispatcher_Standard->dispatch(Object(Zend_Controller_Request_HttpTestCase), Object(Zend_Controller_Response*HttpTestCase))
#16 C:\Users\Sebastian Hoitz\Documents\Entwicklung\kt*api\trunk\library\Zend\Test\PHPUnit\ControllerTestCase.php(199): Zend_Controller*Front->dispatch()
#17 C:\Users\Sebastian Hoitz\Documents\Entwicklung\kt*api\trunk\tests\application\controllers\TicketControllerTest.php(220): Zend_Test_PHPUnit*ControllerTestCase->dispatch('/ticket/1')
#18 [internal function]: TicketControllerTest->testUpdateTicketWithoutInvolvedContactsDoesNotCauseException()
#19 C:\Program Files (x86)\PHP\PEAR\pear\PHPUnit\Framework\TestCase.php(769): ReflectionMethod->invokeArgs(Object(TicketControllerTest), Array)
#20 C:\Program Files (x86)\PHP\PEAR\pear\PHPUnit\Framework\TestCase.php(659): PHPUnit*Framework*TestCase->runTest()
#21 C:\Program Files (x86)\PHP\PEAR\pear\PHPUnit\Framework\TestResult.php(617): PHPUnit*Framework*TestCase->runBare()
#22 C:\Program Files (x86)\PHP\PEAR\pear\PHPUnit\Framework\TestCase.php(607): PHPUnit*Framework*TestResult->run(Object(TicketControllerTest))
#23 C:\Program Files (x86)\PHP\PEAR\pear\PHPUnit\Framework\TestSuite.php(751): PHPUnit*Framework_TestCase->run(Object(PHPUnit_Framework*TestResult))
#24 C:\Program Files (x86)\PHP\PEAR\pear\PHPUnit\Framework\TestSuite.php(727): PHPUnit*Framework_TestSuite->runTest(Object(TicketControllerTest), Object(PHPUnit_Framework*TestResult))
#25 C:\Program Files (x86)\PHP\PEAR\pear\PHPUnit\Framework\TestSuite.php(687): PHPUnit*Framework_TestSuite->run(Object(PHPUnit_Framework*TestResult), false, Array, Array, false)
#26 C:\Program Files (x86)\PHP\PEAR\pear\PHPUnit\TextUI\TestRunner.php(305): PHPUnit*Framework_TestSuite->run(Object(PHPUnit_Framework*TestResult), false, Array, Array, false)
#27 C:\Program Files (x86)\PHP\PEAR\pear\PHPUnit\TextUI\Command.php(188): PHPUnit*TextUI_TestRunner->doRun(Object(PHPUnit_Framework*TestSuite), Array)
#28 C:\Program Files (x86)\PHP\PEAR\pear\PHPUnit\TextUI\Command.php(129): PHPUnit*TextUI*Command->run(Array, true)
#29 C:\Program Files (x86)\PHP\PEAR\phpunit(53): PHPUnit*TextUI*Command::main()
#30 {main}

I assume that this might happen, because of the Class B holding one Class C, and Class A also holding some Class C instances.

Those are, in some cases, the same. So when a new Class B is added, together with a new Class C, this new Class C is also added to Class A.
And somehow internally the already persisted Class C (Class B is getting persisted first) transforms the Class C instance into an array, and Doctrine can't save it anymore.

This is my guess of what happens. When I skip adding all the Class C instances to Class A, I don't get this error.

Originally created by @doctrinebot on GitHub (Oct 19, 2010). Jira issue originally created by user sebastian.hoitz: I have a model which looks like this: ``` Class A protected $collectionB = array(); // Holds many Class B instances protected $collectionC = array(); // Holds many Class C instances Class B protected $classC; // Holds one Class C instance Class C protected $attributes; // Holds many attributes which are stored in another entitty with SINGLE_TABLE discriminator ``` When I try to persist my object to the database, Doctrine causes this error: ``` Message: spl*object*hash() expects parameter 1 to be object, array given File: C:\Users\Sebastian Hoitz\Documents\Entwicklung\kt_api\trunk\library\Doctrine\ORM\UnitOfWork.php Line: 2043 Trace: #0 [internal function]: PHPUnit*Util_ErrorHandler::handleError(2, 'spl_object*hash...', 'C:\Users\Sebast...', 2043, Array) #1 C:\Users\Sebastian Hoitz\Documents\Entwicklung\kt*api\trunk\library\Doctrine\ORM\UnitOfWork.php(2043): spl_object*hash(Array) #2 C:\Users\Sebastian Hoitz\Documents\Entwicklung\kt_api\trunk\library\Doctrine\ORM\Persisters\ManyToManyPersister.php(110): Doctrine\ORM\UnitOfWork->getEntityIdentifier(Array) #3 C:\Users\Sebastian Hoitz\Documents\Entwicklung\kt*api\trunk\library\Doctrine\ORM\Persisters\ManyToManyPersister.php(92): Doctrine\ORM\Persisters\ManyToManyPersister->*collectJoinTableColumnParameters(Object(Doctrine\ORM\PersistentCollection), Array) #4 C:\Users\Sebastian Hoitz\Documents\Entwicklung\kt*api\trunk\library\Doctrine\ORM\Persisters\AbstractCollectionPersister.php(124): Doctrine\ORM\Persisters\ManyToManyPersister->*getInsertRowSQLParameters(Object(Doctrine\ORM\PersistentCollection), Array) #5 C:\Users\Sebastian Hoitz\Documents\Entwicklung\kt_api\trunk\library\Doctrine\ORM\Persisters\AbstractCollectionPersister.php(104): Doctrine\ORM\Persisters\AbstractCollectionPersister->insertRows(Object(Doctrine\ORM\PersistentCollection)) #6 C:\Users\Sebastian Hoitz\Documents\Entwicklung\kt_api\trunk\library\Doctrine\ORM\UnitOfWork.php(303): Doctrine\ORM\Persisters\AbstractCollectionPersister->update(Object(Doctrine\ORM\PersistentCollection)) #7 C:\Users\Sebastian Hoitz\Documents\Entwicklung\kt_api\trunk\library\Doctrine\ORM\EntityManager.php(320): Doctrine\ORM\UnitOfWork->commit() #8 C:\Users\Sebastian Hoitz\Documents\Entwicklung\kt_models\trunk\library\App\Model\Service\Dao\Doctrine.php(26): Doctrine\ORM\EntityManager->flush() #9 C:\Users\Sebastian Hoitz\Documents\Entwicklung\kt*models\trunk\library\App\Model\Service\Abstract.php(54): App_Model_Service_Dao_Doctrine->save(Object(App_Model*Ticket)) #10 C:\Users\Sebastian Hoitz\Documents\Entwicklung\kt*models\trunk\library\App\Model\Abstract.php(264): App_Model_Service_Abstract->save(Object(App_Model*Ticket)) #11 C:\Users\Sebastian Hoitz\Documents\Entwicklung\kt*models\trunk\library\App\Model\Ticket.php(75): App_Model*Abstract->save() #12 C:\Users\Sebastian Hoitz\Documents\Entwicklung\kt*api\trunk\application\controllers\TicketController.php(69): App_Model*Ticket->save() #13 C:\Users\Sebastian Hoitz\Documents\Entwicklung\kt_api\trunk\library\Zend\Controller\Action.php(513): TicketController->putAction() #14 C:\Users\Sebastian Hoitz\Documents\Entwicklung\kt*api\trunk\library\Zend\Controller\Dispatcher\Standard.php(295): Zend_Controller*Action->dispatch('putAction') #15 C:\Users\Sebastian Hoitz\Documents\Entwicklung\kt*api\trunk\library\Zend\Controller\Front.php(954): Zend_Controller_Dispatcher_Standard->dispatch(Object(Zend_Controller_Request_HttpTestCase), Object(Zend_Controller_Response*HttpTestCase)) #16 C:\Users\Sebastian Hoitz\Documents\Entwicklung\kt*api\trunk\library\Zend\Test\PHPUnit\ControllerTestCase.php(199): Zend_Controller*Front->dispatch() #17 C:\Users\Sebastian Hoitz\Documents\Entwicklung\kt*api\trunk\tests\application\controllers\TicketControllerTest.php(220): Zend_Test_PHPUnit*ControllerTestCase->dispatch('/ticket/1') #18 [internal function]: TicketControllerTest->testUpdateTicketWithoutInvolvedContactsDoesNotCauseException() #19 C:\Program Files (x86)\PHP\PEAR\pear\PHPUnit\Framework\TestCase.php(769): ReflectionMethod->invokeArgs(Object(TicketControllerTest), Array) #20 C:\Program Files (x86)\PHP\PEAR\pear\PHPUnit\Framework\TestCase.php(659): PHPUnit*Framework*TestCase->runTest() #21 C:\Program Files (x86)\PHP\PEAR\pear\PHPUnit\Framework\TestResult.php(617): PHPUnit*Framework*TestCase->runBare() #22 C:\Program Files (x86)\PHP\PEAR\pear\PHPUnit\Framework\TestCase.php(607): PHPUnit*Framework*TestResult->run(Object(TicketControllerTest)) #23 C:\Program Files (x86)\PHP\PEAR\pear\PHPUnit\Framework\TestSuite.php(751): PHPUnit*Framework_TestCase->run(Object(PHPUnit_Framework*TestResult)) #24 C:\Program Files (x86)\PHP\PEAR\pear\PHPUnit\Framework\TestSuite.php(727): PHPUnit*Framework_TestSuite->runTest(Object(TicketControllerTest), Object(PHPUnit_Framework*TestResult)) #25 C:\Program Files (x86)\PHP\PEAR\pear\PHPUnit\Framework\TestSuite.php(687): PHPUnit*Framework_TestSuite->run(Object(PHPUnit_Framework*TestResult), false, Array, Array, false) #26 C:\Program Files (x86)\PHP\PEAR\pear\PHPUnit\TextUI\TestRunner.php(305): PHPUnit*Framework_TestSuite->run(Object(PHPUnit_Framework*TestResult), false, Array, Array, false) #27 C:\Program Files (x86)\PHP\PEAR\pear\PHPUnit\TextUI\Command.php(188): PHPUnit*TextUI_TestRunner->doRun(Object(PHPUnit_Framework*TestSuite), Array) #28 C:\Program Files (x86)\PHP\PEAR\pear\PHPUnit\TextUI\Command.php(129): PHPUnit*TextUI*Command->run(Array, true) #29 C:\Program Files (x86)\PHP\PEAR\phpunit(53): PHPUnit*TextUI*Command::main() #30 {main} ``` I assume that this might happen, because of the Class B holding one Class C, and Class A also holding some Class C instances. Those are, in some cases, the same. So when a new Class B is added, together with a new Class C, this new Class C is also added to Class A. And somehow internally the already persisted Class C (Class B is getting persisted first) transforms the Class C instance into an array, and Doctrine can't save it anymore. This is my guess of what happens. When I skip adding all the Class C instances to Class A, I don't get this error.
admin added the Bug label 2026-01-22 12:59:48 +01:00
Sign in to join this conversation.
1 Participants
Notifications
Due Date
No due date set.
Dependencies

No dependencies set.

Reference: doctrine/archived-orm#1041