Overview

Namespaces

  • None
  • Peridot
    • Leo
      • Formatter
      • Interfaces
        • Assert
      • Matcher
        • Template
      • ObjectPath
      • Responder
  • PHP

Classes

  • ObjectPath
  • ObjectPathValue
  • Overview
  • Namespace
  • Class
  • Tree
  1: <?php
  2: namespace Peridot\Leo\ObjectPath;
  3: 
  4: /**
  5:  * ObjectPath is a utility for parsing object and array strings into
  6:  * ObjectPathValues.
  7:  *
  8:  * @package Peridot\Leo\Utility
  9:  */
 10: class ObjectPath
 11: {
 12:     /**
 13:      * The subject to match path expressions against.
 14:      *
 15:      * @var array|object
 16:      */
 17:     protected $subject;
 18: 
 19:     /**
 20:      * A pattern for matching array keys
 21:      *
 22:      * @var string
 23:      */
 24:     private static $arrayKey = '/\[([^\]]+)\]/';
 25: 
 26:     /**
 27:      * @param array|object $subject
 28:      */
 29:     public function __construct($subject)
 30:     {
 31:         $this->subject = $subject;
 32:     }
 33: 
 34:     /**
 35:      * Returns an ObjectPathValue if the property described by $path
 36:      * can be located in the subject.
 37:      *
 38:      * A path expression uses object and array syntax.
 39:      *
 40:      * @code
 41:      *
 42:      * $person = new stdClass();
 43:      * $person->name = new stdClass();
 44:      * $person->name->first = 'brian';
 45:      * $person->name->last = 'scaturro';
 46:      * $person->hobbies = ['programming', 'reading', 'board games'];
 47:      *
 48:      * $path = new ObjectPath($person);
 49:      * $first = $path->get('name->first');
 50:      * $reading = $path->get('hobbies[0]');
 51:      *
 52:      * @endcode
 53:      *
 54:      * @param string $path
 55:      * @return ObjectPathValue
 56:      */
 57:     public function get($path)
 58:     {
 59:         $parts = $this->getPathParts($path);
 60:         $properties = $this->getPropertyCollection($this->subject);
 61:         $pathValue = null;
 62:         while ($properties && $parts) {
 63:             $key = array_shift($parts);
 64:             $key = $this->normalizeKey($key);
 65:             $pathValue = array_key_exists($key, $properties) ? new ObjectPathValue($key, $properties[$key]) : null;
 66: 
 67:             if (! array_key_exists($key, $properties)) {
 68:                 break;
 69:             }
 70: 
 71:             $properties = $this->getPropertyCollection($properties[$key]);
 72:         }
 73:         return $pathValue;
 74:     }
 75: 
 76:     /**
 77:      * Breaks a path expression into an array used
 78:      * for navigating a path.
 79:      *
 80:      * @param $path
 81:      * @return array
 82:      */
 83:     public function getPathParts($path)
 84:     {
 85:         $path = preg_replace('/\[/', '->[', $path);
 86:         if (preg_match('/^->/', $path)) {
 87:             $path = substr($path, 2);
 88:         }
 89: 
 90:         return explode('->', $path);
 91:     }
 92: 
 93:     /**
 94:      * Returns a property as an array.
 95:      *
 96:      * @param $subject
 97:      * @return array
 98:      */
 99:     protected function getPropertyCollection($subject)
100:     {
101:         if (is_object($subject)) {
102:             return get_object_vars($subject);
103:         }
104: 
105:         return $subject;
106:     }
107: 
108:     /**
109:      * Return a key that can be used on the current subject.
110:      *
111:      * @param $key
112:      * @param $matches
113:      * @return mixed
114:      */
115:     protected function normalizeKey($key)
116:     {
117:         if (preg_match(static::$arrayKey, $key, $matches)) {
118:             $key = $matches[1];
119:             return $key;
120:         }
121:         return $key;
122:     }
123: }
124: 
Leo API documentation generated by ApiGen