3 use PayPal\Core\PPUtils;
7 abstract class PPMessage
11 * @param string $prefix
14 public function toNVPString($prefix = '')
17 foreach (get_object_vars($this) as $property => $defaultValue) {
19 if (($propertyValue = $this->{$property}) === NULL || $propertyValue == NULL) {
23 if (is_object($propertyValue)) {
24 $nvp[] = $propertyValue->toNVPString($prefix . $property . '.'); // prefix
26 } elseif (is_array($defaultValue) || is_array($propertyValue)) {
27 foreach (array_values($propertyValue) as $i => $item) {
28 if (!is_object($item)){
29 $nvp[] = $prefix . $property . "($i)" . '=' . urlencode($item);
31 $nvp[] = $item->toNVPString($prefix . $property . "($i).");
36 // Handle classes with attributes
37 if($property == 'value' && ($anno = PPUtils::propertyAnnotations($this, $property)) != NULL && isset($anno['value']) ) {
38 $nvpKey = substr($prefix, 0, -1); // Remove the ending '.'
40 $nvpKey = $prefix . $property ;
42 $nvp[] = $nvpKey . '=' . urlencode($propertyValue);
46 return implode('&', $nvp);
53 * @param string $prefix
55 public function init(array $map = array(), $prefix = '')
61 $map = PPUtils::lowerKeys($map);
63 foreach (get_object_vars($this) as $property => $defaultValue) {
64 if (array_key_exists($propKey = strtolower($prefix . $property), $map) &&
65 $this->isBuiltInType(($type = PPUtils::propertyType($this, $property)))){
66 $type = PPUtils::propertyType($this, $property);
67 $this->{$property} = urldecode($map[$propKey]);
70 } elseif (!$filtered = PPUtils::filterKeyPrefix($map, $propKey)) {
74 if (!class_exists($type = PPUtils::propertyType($this, $property)) && !$this->isBuiltInType($type)) {
75 trigger_error("Class $type not found.", E_USER_NOTICE);
76 continue; // just ignore
79 if (is_array($defaultValue) || PPUtils::isPropertyArray($this, $property)) { // array of objects
80 if($this->isBuiltInType($type)) { // Array of simple types
81 foreach($filtered as $key => $value) {
82 $this->{$property}[trim($key, "()")] = urldecode($value);
84 } else { // Array of complex objects
86 for ($i = 0; $itemValues = PPUtils::filterKeyPrefix($filtered, "($i)") ;$i++) {
87 $this->{$property}[$i] = $item = new $type();
88 $item->init(PPUtils::filterKeyPrefix($itemValues, "."));
89 if(array_key_exists("", $itemValues)) {
90 $item->value = urldecode($itemValues[""]);
93 // Handle cases where we have a list of objects
94 // with just the value present and all attributes values are null
95 foreach($filtered as $key => $value) {
96 $idx = trim($key, "()");
97 if(is_numeric($idx) && (is_null($this->{$property}) || !array_key_exists($idx, $this->{$property})) ) {
98 $this->{$property}[$idx] = new $type;
99 $this->{$property}[$idx]->value = urldecode($value);
103 } else { // one object
104 $this->{$property} = new $type();
105 $this->{$property}->init(PPUtils::filterKeyPrefix($filtered, '.')); // unprefix
106 if(array_key_exists("", $filtered)) {
107 $this->{$property}->value = urldecode($filtered[""]);
113 private function isBuiltInType($typeName) {
114 static $types = array('string', 'int', 'integer', 'bool', 'boolean', 'float', 'decimal', 'long', 'datetime', 'double');
115 return in_array(strtolower($typeName), $types);