1<?php 2 3namespace dokuwiki\Remote\OpenApiDoc; 4 5class Type 6{ 7 protected $typehint; 8 protected $context; 9 10 /** 11 * @param string $typehint The typehint as read from the docblock 12 * @param string $context A fully qualified class name in which context the typehint is used 13 */ 14 public function __construct($typehint, $context = '') 15 { 16 $this->typehint = $typehint; 17 $this->context = $context; 18 } 19 20 /** 21 * Return the typehint as read from the docblock 22 * 23 * @return string 24 */ 25 public function __toString() 26 { 27 return $this->typehint; 28 } 29 30 /** 31 * Return the base type 32 * 33 * This is the type this variable is. Eg. a string[] is an array. 34 * 35 * @return string 36 */ 37 public function getBaseType() 38 { 39 $typehint = $this->typehint; 40 41 if (str_ends_with($typehint, '[]')) { 42 return 'array'; 43 } 44 45 if (in_array($typehint, ['boolean', 'false', 'true'])) { 46 return 'bool'; 47 } 48 49 if (in_array($typehint, ['integer', 'date'])) { 50 return 'int'; 51 } 52 53 if ($typehint === 'file') { 54 return 'string'; 55 } 56 57 // fully qualified class name 58 if ($typehint[0] === '\\') { 59 return ltrim($typehint, '\\'); 60 } 61 62 // relative class name, try to resolve 63 if ($this->context && ctype_upper($typehint[0])) { 64 return ClassResolver::getInstance()->resolve($typehint, $this->context); 65 } 66 67 return $typehint; 68 } 69 70 /** 71 * Return a primitive type understood by the XMLRPC server 72 * 73 * @param string $typehint 74 * @return string 75 */ 76 public function getJSONRPCType() 77 { 78 return $this->getBaseType(); 79 } 80 81 /** 82 * Get the base type as one of the supported OpenAPI types 83 * 84 * Formats (eg. int32 or double) are not supported 85 * 86 * @link https://swagger.io/docs/specification/data-models/data-types/ 87 * @return string 88 */ 89 public function getOpenApiType() 90 { 91 switch ($this->getBaseType()) { 92 case 'int': 93 return 'integer'; 94 case 'bool': 95 return 'boolean'; 96 case 'array': 97 return 'array'; 98 case 'string': 99 case 'mixed': 100 return 'string'; 101 case 'double': 102 case 'float': 103 return 'number'; 104 default: 105 return 'object'; 106 } 107 } 108 109 110 /** 111 * If this is an array, return the type of the array elements 112 * 113 * @return Type|null null if this is not a typed array 114 */ 115 public function getSubType() 116 { 117 $type = $this->typehint; 118 if (!str_ends_with($type, '[]')) { 119 return null; 120 } 121 $type = substr($type, 0, -2); 122 return new Type($type, $this->context); 123 } 124 125 /** 126 * Return a type understood by the XMLRPC server 127 * 128 * @return string 129 */ 130 public function getXMLRPCType() 131 { 132 $type = $this->typehint; 133 134 // keep custom types 135 if (in_array($type, ['date', 'file', 'struct'])) { 136 return $type; 137 } 138 139 $type = $this->getBaseType($this->typehint); 140 141 // primitive types 142 if (in_array($type, ['int', 'string', 'double', 'bool', 'array'])) { 143 return $type; 144 } 145 146 // everything else is an object 147 return 'object'; //should this return 'struct'? 148 } 149} 150