diff --git a/CHANGELOG.md b/CHANGELOG.md index d611db7384c..63992158ee6 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -10,6 +10,7 @@ - Fixes internal cache saving in `Phalcon\Mvc\Model\Binder` when no cache backend is used - Added the ability to get original values from `Phalcon\Mvc\Model\Binder`, added `Phalcon\Mvc\Micro::getModelBinder`, `Phalcon\Dispatcher::getModelBinder` - Added `prepend` parameter to `Phalcon\Loader::register` to specify autoloader's loading order to top most +- Fixed `Phalcon\Session\Bag::remove` to initialize the bag before removing a value # [3.0.4](https://github.com/phalcon/cphalcon/releases/tag/v3.0.4) (XXXX-XX-XX) - Fixed Isnull check is not correct when the model field defaults to an empty string. [#12507](https://github.com/phalcon/cphalcon/issues/12507) diff --git a/phalcon/session/bag.zep b/phalcon/session/bag.zep index 21356525473..6550b568ff5 100644 --- a/phalcon/session/bag.zep +++ b/phalcon/session/bag.zep @@ -231,6 +231,10 @@ class Bag implements InjectionAwareInterface, BagInterface, \IteratorAggregate, */ public function remove(string! property) -> boolean { + if this->_initialized === false { + this->initialize(); + } + var data; let data = this->_data; diff --git a/tests/unit/Session/BagTest.php b/tests/unit/Session/BagTest.php index a8ae07b714f..20bc3cb0ac7 100644 --- a/tests/unit/Session/BagTest.php +++ b/tests/unit/Session/BagTest.php @@ -83,4 +83,45 @@ function () { } ); } + + /** + * Delete a value in a bag (not initialized internally) + * + * @author Fabio Mora + * @since 2017-02-21 + */ + public function testDeleteInitializeInternalData() + { + $this->specify( + "Delete a value in a non initialized bag has failed", + function () { + $reflectionClass = new \ReflectionClass(\Phalcon\Session\Bag::class); + $_data = $reflectionClass->getProperty('_data'); + $_data->setAccessible(true); + $_initialized = $reflectionClass->getProperty('_initialized'); + $_initialized->setAccessible(true); + + // Setup a bag with a value + $bag = new \Phalcon\Session\Bag('fruit'); + $bag->set('apples', 10); + expect($bag->get('apples'))->same(10); + expect($_data->getValue($bag))->same(['apples' => 10]); + expect($_initialized->getValue($bag))->true(); + + // Emulate a reset of the internal status (e.g. as would be done by a sleep/wakeup handler) + $serializedBag = serialize($bag); + unset($bag); + + $bag = unserialize($serializedBag); + $_data->setValue($bag, null); + $_initialized->setValue($bag, false); + + // Delete + expect($_initialized->getValue($bag))->false(); + expect($bag->remove('apples'))->true(); + expect($bag->get('apples'))->null(); + expect($_initialized->getValue($bag))->true(); + } + ); + } }