CakePHP
  • Documentation
    • Book
    • API
    • Videos
    • Logos & Trademarks
  • Business Solutions
  • Swag
  • Road Trip
  • Team
  • Community
    • Community
    • Team
    • Issues (Github)
    • YouTube Channel
    • Get Involved
    • Bakery
    • Featured Resources
    • Newsletter
    • Certification
    • My CakePHP
    • CakeFest
    • Facebook
    • Twitter
    • Help & Support
    • Forum
    • Stack Overflow
    • IRC
    • Slack
    • Paid Support
CakePHP

C CakePHP 3.7 Red Velvet API

  • Overview
  • Tree
  • Deprecated
  • Version:
    • 3.7
      • 3.7
      • 3.6
      • 3.5
      • 3.4
      • 3.3
      • 3.2
      • 3.1
      • 3.0
      • 2.10
      • 2.9
      • 2.8
      • 2.7
      • 2.6
      • 2.5
      • 2.4
      • 2.3
      • 2.2
      • 2.1
      • 2.0
      • 1.3
      • 1.2

Namespaces

  • Cake
    • Auth
      • Storage
    • Cache
      • Engine
    • Collection
      • Iterator
    • Command
    • Console
      • Exception
    • Controller
      • Component
      • Exception
    • Core
      • Configure
        • Engine
      • Exception
      • Retry
    • Database
      • Driver
      • Exception
      • Expression
      • Schema
      • Statement
      • Type
    • Datasource
      • Exception
    • Error
      • Middleware
    • Event
      • Decorator
    • Filesystem
    • Form
    • Http
      • Client
        • Adapter
        • Auth
      • Cookie
      • Exception
      • Middleware
      • Session
    • I18n
      • Formatter
      • Middleware
      • Parser
    • Log
      • Engine
    • Mailer
      • Exception
      • Transport
    • Network
      • Exception
    • ORM
      • Association
      • Behavior
        • Translate
      • Exception
      • Locator
      • Rule
    • Routing
      • Exception
      • Filter
      • Middleware
      • Route
    • Shell
      • Helper
      • Task
    • TestSuite
      • Fixture
      • Stub
    • Utility
      • Exception
    • Validation
    • View
      • Exception
      • Form
      • Helper
      • Widget
  • None

Classes

  • Cookie
  • CookieCollection

Interfaces

  • CookieInterface
  1: <?php
  2: /**
  3:  * CakePHP(tm) : Rapid Development Framework (http://cakephp.org)
  4:  * Copyright (c) Cake Software Foundation, Inc. (http://cakefoundation.org)
  5:  *
  6:  * Licensed under The MIT License
  7:  * Redistributions of files must retain the above copyright notice.
  8:  *
  9:  * @copyright     Copyright (c) Cake Software Foundation, Inc. (http://cakefoundation.org)
 10:  * @link          http://cakephp.org CakePHP(tm) Project
 11:  * @since         3.5.0
 12:  * @license       http://www.opensource.org/licenses/mit-license.php MIT License
 13:  */
 14: namespace Cake\Http\Cookie;
 15: 
 16: use Cake\Chronos\Chronos;
 17: use Cake\Utility\Hash;
 18: use DateTimeImmutable;
 19: use DateTimeZone;
 20: use InvalidArgumentException;
 21: 
 22: /**
 23:  * Cookie object to build a cookie and turn it into a header value
 24:  *
 25:  * An HTTP cookie (also called web cookie, Internet cookie, browser cookie or
 26:  * simply cookie) is a small piece of data sent from a website and stored on
 27:  * the user's computer by the user's web browser while the user is browsing.
 28:  *
 29:  * Cookies were designed to be a reliable mechanism for websites to remember
 30:  * stateful information (such as items added in the shopping cart in an online
 31:  * store) or to record the user's browsing activity (including clicking
 32:  * particular buttons, logging in, or recording which pages were visited in
 33:  * the past). They can also be used to remember arbitrary pieces of information
 34:  * that the user previously entered into form fields such as names, and preferences.
 35:  *
 36:  * Cookie objects are immutable, and you must re-assign variables when modifying
 37:  * cookie objects:
 38:  *
 39:  * ```
 40:  * $cookie = $cookie->withValue('0');
 41:  * ```
 42:  *
 43:  * @link https://tools.ietf.org/html/rfc6265
 44:  * @link https://en.wikipedia.org/wiki/HTTP_cookie
 45:  * @see Cake\Http\Cookie\CookieCollection for working with collections of cookies.
 46:  * @see Cake\Http\Response::getCookieCollection() for working with response cookies.
 47:  */
 48: class Cookie implements CookieInterface
 49: {
 50: 
 51:     /**
 52:      * Cookie name
 53:      *
 54:      * @var string
 55:      */
 56:     protected $name = '';
 57: 
 58:     /**
 59:      * Raw Cookie value.
 60:      *
 61:      * @var string|array
 62:      */
 63:     protected $value = '';
 64: 
 65:     /**
 66:      * Whether or not a JSON value has been expanded into an array.
 67:      *
 68:      * @var bool
 69:      */
 70:     protected $isExpanded = false;
 71: 
 72:     /**
 73:      * Expiration time
 74:      *
 75:      * @var \DateTime|\DateTimeImmutable|null
 76:      */
 77:     protected $expiresAt;
 78: 
 79:     /**
 80:      * Path
 81:      *
 82:      * @var string
 83:      */
 84:     protected $path = '/';
 85: 
 86:     /**
 87:      * Domain
 88:      *
 89:      * @var string
 90:      */
 91:     protected $domain = '';
 92: 
 93:     /**
 94:      * Secure
 95:      *
 96:      * @var bool
 97:      */
 98:     protected $secure = false;
 99: 
100:     /**
101:      * HTTP only
102:      *
103:      * @var bool
104:      */
105:     protected $httpOnly = false;
106: 
107:     /**
108:      * Constructor
109:      *
110:      * The constructors args are similar to the native PHP `setcookie()` method.
111:      * The only difference is the 3rd argument which excepts null or an
112:      * DateTime or DateTimeImmutable object instead an integer.
113:      *
114:      * @link http://php.net/manual/en/function.setcookie.php
115:      * @param string $name Cookie name
116:      * @param string|array $value Value of the cookie
117:      * @param \DateTime|\DateTimeImmutable|null $expiresAt Expiration time and date
118:      * @param string $path Path
119:      * @param string $domain Domain
120:      * @param bool $secure Is secure
121:      * @param bool $httpOnly HTTP Only
122:      */
123:     public function __construct(
124:         $name,
125:         $value = '',
126:         $expiresAt = null,
127:         $path = '/',
128:         $domain = '',
129:         $secure = false,
130:         $httpOnly = false
131:     ) {
132:         $this->validateName($name);
133:         $this->name = $name;
134: 
135:         $this->_setValue($value);
136: 
137:         $this->validateString($domain);
138:         $this->domain = $domain;
139: 
140:         $this->validateBool($httpOnly);
141:         $this->httpOnly = $httpOnly;
142: 
143:         $this->validateString($path);
144:         $this->path = $path;
145: 
146:         $this->validateBool($secure);
147:         $this->secure = $secure;
148:         if ($expiresAt) {
149:             $expiresAt = $expiresAt->setTimezone(new DateTimeZone('GMT'));
150:         }
151:         $this->expiresAt = $expiresAt;
152:     }
153: 
154:     /**
155:      * Returns a header value as string
156:      *
157:      * @return string
158:      */
159:     public function toHeaderValue()
160:     {
161:         $value = $this->value;
162:         if ($this->isExpanded) {
163:             $value = $this->_flatten($this->value);
164:         }
165:         $headerValue[] = sprintf('%s=%s', $this->name, rawurlencode($value));
166: 
167:         if ($this->expiresAt) {
168:             $headerValue[] = sprintf('expires=%s', $this->getFormattedExpires());
169:         }
170:         if ($this->path !== '') {
171:             $headerValue[] = sprintf('path=%s', $this->path);
172:         }
173:         if ($this->domain !== '') {
174:             $headerValue[] = sprintf('domain=%s', $this->domain);
175:         }
176:         if ($this->secure) {
177:             $headerValue[] = 'secure';
178:         }
179:         if ($this->httpOnly) {
180:             $headerValue[] = 'httponly';
181:         }
182: 
183:         return implode('; ', $headerValue);
184:     }
185: 
186:     /**
187:      * {@inheritDoc}
188:      */
189:     public function withName($name)
190:     {
191:         $this->validateName($name);
192:         $new = clone $this;
193:         $new->name = $name;
194: 
195:         return $new;
196:     }
197: 
198:     /**
199:      * {@inheritDoc}
200:      */
201:     public function getId()
202:     {
203:         return "{$this->name};{$this->domain};{$this->path}";
204:     }
205: 
206:     /**
207:      * {@inheritDoc}
208:      */
209:     public function getName()
210:     {
211:         return $this->name;
212:     }
213: 
214:     /**
215:      * Validates the cookie name
216:      *
217:      * @param string $name Name of the cookie
218:      * @return void
219:      * @throws \InvalidArgumentException
220:      * @link https://tools.ietf.org/html/rfc2616#section-2.2 Rules for naming cookies.
221:      */
222:     protected function validateName($name)
223:     {
224:         if (preg_match("/[=,;\t\r\n\013\014]/", $name)) {
225:             throw new InvalidArgumentException(
226:                 sprintf('The cookie name `%s` contains invalid characters.', $name)
227:             );
228:         }
229: 
230:         if (empty($name)) {
231:             throw new InvalidArgumentException('The cookie name cannot be empty.');
232:         }
233:     }
234: 
235:     /**
236:      * {@inheritDoc}
237:      */
238:     public function getValue()
239:     {
240:         return $this->value;
241:     }
242: 
243:     /**
244:      * {@inheritDoc}
245:      */
246:     public function getStringValue()
247:     {
248:         if ($this->isExpanded) {
249:             return $this->_flatten($this->value);
250:         }
251: 
252:         return $this->value;
253:     }
254: 
255:     /**
256:      * {@inheritDoc}
257:      */
258:     public function withValue($value)
259:     {
260:         $new = clone $this;
261:         $new->_setValue($value);
262: 
263:         return $new;
264:     }
265: 
266:     /**
267:      * Setter for the value attribute.
268:      *
269:      * @param mixed $value The value to store.
270:      * @return void
271:      */
272:     protected function _setValue($value)
273:     {
274:         $this->isExpanded = is_array($value);
275:         $this->value = $value;
276:     }
277: 
278:     /**
279:      * {@inheritDoc}
280:      */
281:     public function withPath($path)
282:     {
283:         $this->validateString($path);
284:         $new = clone $this;
285:         $new->path = $path;
286: 
287:         return $new;
288:     }
289: 
290:     /**
291:      * {@inheritDoc}
292:      */
293:     public function getPath()
294:     {
295:         return $this->path;
296:     }
297: 
298:     /**
299:      * {@inheritDoc}
300:      */
301:     public function withDomain($domain)
302:     {
303:         $this->validateString($domain);
304:         $new = clone $this;
305:         $new->domain = $domain;
306: 
307:         return $new;
308:     }
309: 
310:     /**
311:      * {@inheritDoc}
312:      */
313:     public function getDomain()
314:     {
315:         return $this->domain;
316:     }
317: 
318:     /**
319:      * Validate that an argument is a string
320:      *
321:      * @param string $value The value to validate.
322:      * @return void
323:      * @throws \InvalidArgumentException
324:      */
325:     protected function validateString($value)
326:     {
327:         if (!is_string($value)) {
328:             throw new InvalidArgumentException(sprintf(
329:                 'The provided arg must be of type `string` but `%s` given',
330:                 gettype($value)
331:             ));
332:         }
333:     }
334: 
335:     /**
336:      * {@inheritDoc}
337:      */
338:     public function isSecure()
339:     {
340:         return $this->secure;
341:     }
342: 
343:     /**
344:      * {@inheritDoc}
345:      */
346:     public function withSecure($secure)
347:     {
348:         $this->validateBool($secure);
349:         $new = clone $this;
350:         $new->secure = $secure;
351: 
352:         return $new;
353:     }
354: 
355:     /**
356:      * {@inheritDoc}
357:      */
358:     public function withHttpOnly($httpOnly)
359:     {
360:         $this->validateBool($httpOnly);
361:         $new = clone $this;
362:         $new->httpOnly = $httpOnly;
363: 
364:         return $new;
365:     }
366: 
367:     /**
368:      * Validate that an argument is a boolean
369:      *
370:      * @param bool $value The value to validate.
371:      * @return void
372:      * @throws \InvalidArgumentException
373:      */
374:     protected function validateBool($value)
375:     {
376:         if (!is_bool($value)) {
377:             throw new InvalidArgumentException(sprintf(
378:                 'The provided arg must be of type `bool` but `%s` given',
379:                 gettype($value)
380:             ));
381:         }
382:     }
383: 
384:     /**
385:      * {@inheritDoc}
386:      */
387:     public function isHttpOnly()
388:     {
389:         return $this->httpOnly;
390:     }
391: 
392:     /**
393:      * {@inheritDoc}
394:      */
395:     public function withExpiry($dateTime)
396:     {
397:         $new = clone $this;
398:         $new->expiresAt = $dateTime->setTimezone(new DateTimeZone('GMT'));
399: 
400:         return $new;
401:     }
402: 
403:     /**
404:      * {@inheritDoc}
405:      */
406:     public function getExpiry()
407:     {
408:         return $this->expiresAt;
409:     }
410: 
411:     /**
412:      * {@inheritDoc}
413:      */
414:     public function getExpiresTimestamp()
415:     {
416:         if (!$this->expiresAt) {
417:             return null;
418:         }
419: 
420:         return $this->expiresAt->format('U');
421:     }
422: 
423:     /**
424:      * {@inheritDoc}
425:      */
426:     public function getFormattedExpires()
427:     {
428:         if (!$this->expiresAt) {
429:             return '';
430:         }
431: 
432:         return $this->expiresAt->format(static::EXPIRES_FORMAT);
433:     }
434: 
435:     /**
436:      * {@inheritDoc}
437:      */
438:     public function isExpired($time = null)
439:     {
440:         $time = $time ?: new DateTimeImmutable('now', new DateTimeZone('UTC'));
441:         if (!$this->expiresAt) {
442:             return false;
443:         }
444: 
445:         return $this->expiresAt < $time;
446:     }
447: 
448:     /**
449:      * {@inheritDoc}
450:      */
451:     public function withNeverExpire()
452:     {
453:         $new = clone $this;
454:         $new->expiresAt = Chronos::createFromDate(2038, 1, 1);
455: 
456:         return $new;
457:     }
458: 
459:     /**
460:      * {@inheritDoc}
461:      */
462:     public function withExpired()
463:     {
464:         $new = clone $this;
465:         $new->expiresAt = Chronos::createFromTimestamp(1);
466: 
467:         return $new;
468:     }
469: 
470:     /**
471:      * Checks if a value exists in the cookie data.
472:      *
473:      * This method will expand serialized complex data,
474:      * on first use.
475:      *
476:      * @param string $path Path to check
477:      * @return bool
478:      */
479:     public function check($path)
480:     {
481:         if ($this->isExpanded === false) {
482:             $this->value = $this->_expand($this->value);
483:         }
484: 
485:         return Hash::check($this->value, $path);
486:     }
487: 
488:     /**
489:      * Create a new cookie with updated data.
490:      *
491:      * @param string $path Path to write to
492:      * @param mixed $value Value to write
493:      * @return static
494:      */
495:     public function withAddedValue($path, $value)
496:     {
497:         $new = clone $this;
498:         if ($new->isExpanded === false) {
499:             $new->value = $new->_expand($new->value);
500:         }
501:         $new->value = Hash::insert($new->value, $path, $value);
502: 
503:         return $new;
504:     }
505: 
506:     /**
507:      * Create a new cookie without a specific path
508:      *
509:      * @param string $path Path to remove
510:      * @return static
511:      */
512:     public function withoutAddedValue($path)
513:     {
514:         $new = clone $this;
515:         if ($new->isExpanded === false) {
516:             $new->value = $new->_expand($new->value);
517:         }
518:         $new->value = Hash::remove($new->value, $path);
519: 
520:         return $new;
521:     }
522: 
523:     /**
524:      * Read data from the cookie
525:      *
526:      * This method will expand serialized complex data,
527:      * on first use.
528:      *
529:      * @param string $path Path to read the data from
530:      * @return mixed
531:      */
532:     public function read($path = null)
533:     {
534:         if ($this->isExpanded === false) {
535:             $this->value = $this->_expand($this->value);
536:         }
537: 
538:         if ($path === null) {
539:             return $this->value;
540:         }
541: 
542:         return Hash::get($this->value, $path);
543:     }
544: 
545:     /**
546:      * Checks if the cookie value was expanded
547:      *
548:      * @return bool
549:      */
550:     public function isExpanded()
551:     {
552:         return $this->isExpanded;
553:     }
554: 
555:     /**
556:      * Implode method to keep keys are multidimensional arrays
557:      *
558:      * @param array $array Map of key and values
559:      * @return string A json encoded string.
560:      */
561:     protected function _flatten(array $array)
562:     {
563:         return json_encode($array);
564:     }
565: 
566:     /**
567:      * Explode method to return array from string set in CookieComponent::_flatten()
568:      * Maintains reading backwards compatibility with 1.x CookieComponent::_flatten().
569:      *
570:      * @param string $string A string containing JSON encoded data, or a bare string.
571:      * @return string|array Map of key and values
572:      */
573:     protected function _expand($string)
574:     {
575:         $this->isExpanded = true;
576:         $first = substr($string, 0, 1);
577:         if ($first === '{' || $first === '[') {
578:             $ret = json_decode($string, true);
579: 
580:             return ($ret !== null) ? $ret : $string;
581:         }
582: 
583:         $array = [];
584:         foreach (explode(',', $string) as $pair) {
585:             $key = explode('|', $pair);
586:             if (!isset($key[1])) {
587:                 return $key[0];
588:             }
589:             $array[$key[0]] = $key[1];
590:         }
591: 
592:         return $array;
593:     }
594: }
595: 
Follow @CakePHP
#IRC
OpenHub
Rackspace
  • Business Solutions
  • Showcase
  • Documentation
  • Book
  • API
  • Videos
  • Logos & Trademarks
  • Community
  • Team
  • Issues (Github)
  • YouTube Channel
  • Get Involved
  • Bakery
  • Featured Resources
  • Newsletter
  • Certification
  • My CakePHP
  • CakeFest
  • Facebook
  • Twitter
  • Help & Support
  • Forum
  • Stack Overflow
  • IRC
  • Slack
  • Paid Support

Generated using CakePHP API Docs