public static function decodeRequest($encodedRequest, ClientOracle $clientOracle) { if ($encodedRequest == null) { throw new NullPointerException('encodedRequest cannot be null'); } if ($encodedRequest == '') { throw new IllegalArgumentException('encodedRequest cannot be empty'); } try { $decoder = null; try { $decoder = new SimplePayloadDecoder($clientOracle, $encodedRequest); } catch (ClassNotFoundException $e) { throw new IncompatibleRemoteServiceException('Server does not have a type sent by the client', $e); } $streamReader = new CommandServerSerializationStreamReader(); if ($decoder->getThrownValue() != null) { $streamReader->prepareToRead(array($decoder->getThrownValue())); throw new RemoteException($streamReader->readObject()); } else { $streamReader->prepareToRead($decoder->getValues()); } $serviceIntfName = $streamReader->readString(); //$servicePhpName = self::serviceInterfaceToPhpService($serviceIntfName); $serviceIntf = self::getClassForSerializedName($serviceIntfName); if (!Classes::classOf('RemoteService')->isAssignableFrom($serviceIntf)) { throw new IncompatibleRemoteServiceException('Blocked attempt to access interface "' . $serviceIntf->getName() . '" which does not extends RemoteService'); } $servicePhpName = $serviceIntf->getName(); $serviceObject = null; try { $serviceObject = new $servicePhpName(); } catch (Exception $e) { throw new IncompatibleRemoteServiceException('Could not locate requested service "' . $serviceIntfName . '"', $e); } $serviceMethodName = $streamReader->readString(); $paramCount = $streamReader->readInt(); $parameterTypes = array(); for ($i = 0; $i < $paramCount; $i++) { $paramClassName = $streamReader->readString(); try { $parameterTypes[] = self::getClassForSerializedName($paramClassName, $clientOracle); } catch (ClassNotFoundException $e) { throw new IncompatibleRemoteServiceException('Parameter ' . $i . ' of is of an unknown type ' . $paramClassName, $e); } } $method = $serviceIntf->getMethod($serviceMethodName); if ($method == null) { throw new IncompatibleRemoteServiceException('Cound not find the method ' . $serviceMethodName . ' in service ' . $serviceIntfName); } $parameterValues = array(); for ($i = 0; $i < $paramCount; $i++) { $parameterValues[] = Accessors::get($parameterTypes[$i])->readNext($streamReader); } return new RpcRequest($serviceObject, $method, $parameterValues); } catch (SerializationException $e) { throw new IncompatibleRemoteServiceException($e->getMessage(), $e); } }
private function makeObject(Clazz $type, $value) { // no anonymous class, and no local class in php $manualType = $type; $customSerializer = null; do { $customSerializer = SerializabilityUtil::hasCustomFieldSerializer($manualType); if ($customSerializer != null) { break; } $manualType = $manualType->getSuperClass(); } while ($manualType != null); $ins = null; if ($customSerializer != null) { $ins = $this->serializeWithCustomSerializer($customSerializer, $value, $type, $manualType); } else { $ins = new InstantiateCommand($type); $this->identityMap->put($value, $ins); } if ($type != $manualType) { if (!Classes::classOf('GWTSerializable')->isAssignableFrom($type) && !Classes::classOf('IsSerializable')->isAssignableFrom($type)) { throw new SerializationException($type->getName() . ' is not a serializable type'); } } while ($type != $manualType) { $serializableFields = $this->clientOracle->getOperableFields($type); foreach ($serializableFields as $declField) { assert($declField != null); //echo '[' . $declField->getName() . ' = ' . $declField->getType() . ']<br />'; $accessor = Accessors::get($declField->getType()); $valueCommand = null; $fieldValue = $accessor->get($value, $declField); if (is_null($fieldValue)) { $valueCommand = NullValueCommand::INSTANCE(); } else { $fieldType = $declField->getType()->isPrimitive() ? $declField->getType() : ($declField->hasType() ? $declField->getType() : Classes::classOfValue($fieldValue)); $valueCommand = $this->makeValue($fieldType, $fieldValue); } //echo '{set ' . $declField->getDeclaringClass()->getName() . ' / ' . $declField->getName() . ' / ' . $valueCommand . '}'; $ins->set($declField->getDeclaringClass(), $declField->getName(), $valueCommand); } $type = $type->getSuperClass(); } return $ins; }