From ba5887eb38bd0e9528ef2b9d1eed21f93239290a Mon Sep 17 00:00:00 2001 From: Mark Story Date: Sat, 18 Mar 2017 22:26:47 -0400 Subject: [PATCH] Start making Cookie immutable. Convert setValue() to withValue() which supports immutable workflows. --- src/Http/Cookie/Cookie.php | 33 ++++++++++++++++++----- src/Http/Cookie/CookieInterface.php | 6 ++--- tests/TestCase/Http/Cookie/CookieTest.php | 14 ++++++++++ 3 files changed, 43 insertions(+), 10 deletions(-) diff --git a/src/Http/Cookie/Cookie.php b/src/Http/Cookie/Cookie.php index 26965059901..91c778ba943 100644 --- a/src/Http/Cookie/Cookie.php +++ b/src/Http/Cookie/Cookie.php @@ -33,6 +33,13 @@ * the past). They can also be used to remember arbitrary pieces of information * that the user previously entered into form fields such as names, and preferences. * + * Cookie objects are immutable, and you must re-assign variables when modifying + * cookie objects: + * + * ``` + * $cookie = $cookie->withValue('0'); + * ``` + * * @link https://tools.ietf.org/html/rfc6265 * @link https://en.wikipedia.org/wiki/HTTP_cookie */ @@ -116,8 +123,8 @@ class Cookie implements CookieInterface public function __construct($name, $value = '', $expiresAt = null, $path = '', $domain = '', $secure = false, $httpOnly = false) { $this->validateName($name); - $this->setName($name); - $this->setValue($value); + $this->name = $name; + $this->_setValue($value); $this->setDomain($domain); $this->setHttpOnly($httpOnly); $this->setPath($path); @@ -223,20 +230,32 @@ public function getValue() } /** - * Sets the raw cookie data + * Create a cookie with an updated value. * * @param string|array $value Value of the cookie to set - * @return $this + * @return static + */ + public function withValue($value) + { + $new = clone $this; + $new->_setValue($value); + + return $new; + } + + /** + * Setter for the value attribute. + * + * @param mixed $value The value to store. + * @return void */ - public function setValue($value) + protected function _setValue($value) { if (is_array($value)) { $this->isExpanded = true; } $this->value = $value; - - return $this; } /** diff --git a/src/Http/Cookie/CookieInterface.php b/src/Http/Cookie/CookieInterface.php index 17413694f00..00924c0e90e 100644 --- a/src/Http/Cookie/CookieInterface.php +++ b/src/Http/Cookie/CookieInterface.php @@ -41,12 +41,12 @@ public function getName(); public function getValue(); /** - * Sets the raw cookie data + * Create a cookie with an updated value. * * @param string|array $value Value of the cookie to set - * @return $this + * @return static */ - public function setValue($value); + public function withValue($value); /** * Returns the cookie as header value diff --git a/tests/TestCase/Http/Cookie/CookieTest.php b/tests/TestCase/Http/Cookie/CookieTest.php index b5d26fc5f88..ab84fa6e230 100644 --- a/tests/TestCase/Http/Cookie/CookieTest.php +++ b/tests/TestCase/Http/Cookie/CookieTest.php @@ -122,6 +122,20 @@ public function testGetValue() $this->assertEquals('', $result); } + /** + * Test setting values in cookies + * + * @return void + */ + public function testWithValue() + { + $cookie = new Cookie('cakephp', 'cakephp-rocks'); + $new = $cookie->withValue('new'); + $this->assertNotSame($new, $cookie, 'Should make a clone'); + $this->assertSame('cakephp-rocks', $cookie->getValue(), 'old instance not modified'); + $this->assertSame('new', $new->getValue()); + } + /** * testInflateAndExpand *