/** * Convert the input array from key-value format to a list of parameters suitable for the specified class / method. * * The input array should have the field name as the key, and the value will either be a primitive or another * key-value array. The top level of this array needs keys that match the names of the parameters on the * service method. * * Mismatched types are caught by the PHP runtime, not explicitly checked for by this code. * * @param string $serviceClassName name of the service class that we are trying to call * @param string $serviceMethodName name of the method that we are trying to call * @param array $inputArray data to send to method in key-value format * @return array list of parameters that can be used to call the service method * @throws InputException if no value is provided for required parameters * @throws WebapiException */ public function process($serviceClassName, $serviceMethodName, array $inputArray) { $inputData = []; $inputError = []; foreach ($this->methodsMap->getMethodParams($serviceClassName, $serviceMethodName) as $param) { $paramName = $param[MethodsMap::METHOD_META_NAME]; $snakeCaseParamName = strtolower(preg_replace("/(?<=\\w)(?=[A-Z])/", "_\$1", $paramName)); if (isset($inputArray[$paramName]) || isset($inputArray[$snakeCaseParamName])) { $paramValue = isset($inputArray[$paramName]) ? $inputArray[$paramName] : $inputArray[$snakeCaseParamName]; try { $inputData[] = $this->convertValue($paramValue, $param[MethodsMap::METHOD_META_TYPE]); } catch (SerializationException $e) { throw new WebapiException(new Phrase($e->getMessage())); } } else { if ($param[MethodsMap::METHOD_META_HAS_DEFAULT_VALUE]) { $inputData[] = $param[MethodsMap::METHOD_META_DEFAULT_VALUE]; } else { $inputError[] = $paramName; } } } $this->processInputError($inputError); return $inputData; }
/** * @param string $serviceName * @param string $methodName * @param string $handlerName * @param string $topicName * @return void */ public function validateResponseHandlersType($serviceName, $methodName, $handlerName, $topicName) { try { $this->methodsMap->getMethodParams($serviceName, $methodName); } catch (\Exception $e) { throw new \LogicException(sprintf('Service method specified in the definition of handler "%s" for topic "%s"' . ' is not available. Given "%s"', $handlerName, $topicName, $serviceName . '::' . $methodName)); } }
/** * Validate service method * * @param string $serviceMethod * @param string $topicName * @param string $className * @param string $methodName * @return void */ public function validateServiceMethod($serviceMethod, $topicName, $className, $methodName) { try { $this->methodsMap->getMethodParams($className, $methodName); } catch (\Exception $e) { throw new \LogicException(sprintf('Service method specified in the definition of topic "%s" is not available. Given "%s"', $topicName, $serviceMethod)); } }
/** * Extract service method metadata. * * @param string $className * @param string $methodName * @return array */ public function extractMethodMetadata($className, $methodName) { $result = [Config::SCHEMA_METHOD_PARAMS => [], Config::SCHEMA_METHOD_RETURN_TYPE => $this->methodsMap->getMethodReturnType($className, $methodName), Config::SCHEMA_METHOD_HANDLER => [Config::HANDLER_TYPE => $className, Config::HANDLER_METHOD => $methodName]]; $paramsMeta = $this->methodsMap->getMethodParams($className, $methodName); foreach ($paramsMeta as $paramPosition => $paramMeta) { $result[Config::SCHEMA_METHOD_PARAMS][] = [Config::SCHEMA_METHOD_PARAM_NAME => $paramMeta[MethodsMap::METHOD_META_NAME], Config::SCHEMA_METHOD_PARAM_POSITION => $paramPosition, Config::SCHEMA_METHOD_PARAM_IS_REQUIRED => !$paramMeta[MethodsMap::METHOD_META_HAS_DEFAULT_VALUE], Config::SCHEMA_METHOD_PARAM_TYPE => $paramMeta[MethodsMap::METHOD_META_TYPE]]; } return $result; }
/** * Get message schema defined by service method signature. * * @param \DOMNode $topicNode * @return array */ protected function extractSchemaDefinedByServiceMethod($topicNode) { $topicAttributes = $topicNode->attributes; if (!$topicAttributes->getNamedItem('schema')) { return null; } $topicName = $topicAttributes->getNamedItem('name')->nodeValue; list($className, $methodName) = $this->parseServiceMethod($topicAttributes->getNamedItem('schema')->nodeValue, $topicName); $result = [Config::SCHEMA_METHOD_PARAMS => [], Config::SCHEMA_METHOD_RETURN_TYPE => $this->methodsMap->getMethodReturnType($className, $methodName), Config::SCHEMA_METHOD_HANDLER => [Config::HANDLER_TYPE => $className, Config::HANDLER_METHOD => $methodName]]; $paramsMeta = $this->methodsMap->getMethodParams($className, $methodName); foreach ($paramsMeta as $paramPosition => $paramMeta) { $result[Config::SCHEMA_METHOD_PARAMS][] = [Config::SCHEMA_METHOD_PARAM_NAME => $paramMeta[MethodsMap::METHOD_META_NAME], Config::SCHEMA_METHOD_PARAM_POSITION => $paramPosition, Config::SCHEMA_METHOD_PARAM_IS_REQUIRED => !$paramMeta[MethodsMap::METHOD_META_HAS_DEFAULT_VALUE], Config::SCHEMA_METHOD_PARAM_TYPE => $paramMeta[MethodsMap::METHOD_META_TYPE]]; } return $result; }