summaryrefslogtreecommitdiff
path: root/framework/Web/Services/TSoapServer.php
diff options
context:
space:
mode:
Diffstat (limited to 'framework/Web/Services/TSoapServer.php')
-rw-r--r--framework/Web/Services/TSoapServer.php345
1 files changed, 345 insertions, 0 deletions
diff --git a/framework/Web/Services/TSoapServer.php b/framework/Web/Services/TSoapServer.php
new file mode 100644
index 00000000..0441e67d
--- /dev/null
+++ b/framework/Web/Services/TSoapServer.php
@@ -0,0 +1,345 @@
+<?php
+/**
+ * TSoapService and TSoapServer class file
+ *
+ * @author Knut Urdalen <knut.urdalen@gmail.com>
+ * @author Qiang Xue <qiang.xue@gmail.com>
+ * @link http://www.pradosoft.com/
+ * @copyright Copyright &copy; 2005-2014 PradoSoft
+ * @license http://www.pradosoft.com/license/
+ * @package System.Web.Services
+ */
+
+
+/**
+ * TSoapServer class.
+ *
+ * TSoapServer is a wrapper of the PHP SoapServer class.
+ * It associates a SOAP provider class to the SoapServer object.
+ * It also manages the URI for the SOAP service and WSDL.
+ *
+ * @author Qiang Xue <qiang.xue@gmail.com>
+ * @package System.Web.Services
+ * @since 3.1
+ */
+class TSoapServer extends TApplicationComponent
+{
+ const WSDL_CACHE_PREFIX='wsdl.';
+
+ private $_id;
+ private $_provider;
+
+ private $_version='';
+ private $_actor='';
+ private $_encoding='';
+ private $_uri='';
+ private $_classMap;
+ private $_persistent=false;
+ private $_wsdlUri='';
+
+ private $_requestedMethod;
+
+ private $_server;
+
+ /**
+ * @return string the ID of the SOAP server
+ */
+ public function getID()
+ {
+ return $this->_id;
+ }
+
+ /**
+ * @param string the ID of the SOAP server
+ * @throws TInvalidDataValueException if the ID ends with '.wsdl'.
+ */
+ public function setID($id)
+ {
+ if(strrpos($this->_id,'.wsdl')===strlen($this->_id)-5)
+ throw new TInvalidDataValueException('soapserver_id_invalid',$id);
+ $this->_id=$id;
+ }
+
+ /**
+ * Handles the SOAP request.
+ */
+ public function run()
+ {
+ if(($provider=$this->getProvider())!==null)
+ {
+ Prado::using($provider);
+ $providerClass=($pos=strrpos($provider,'.'))!==false?substr($provider,$pos+1):$provider;
+ $this->guessMethodCallRequested($providerClass);
+ $server=$this->createServer();
+ $server->setClass($providerClass, $this);
+ if($this->_persistent)
+ $server->setPersistence(SOAP_PERSISTENCE_SESSION);
+ }
+ else
+ $server=$this->createServer();
+ try
+ {
+ $server->handle();
+ }
+ catch (Exception $e)
+ {
+ if($this->getApplication()->getMode()===TApplicationMode::Debug)
+ $this->fault($e->getMessage(), $e->__toString());
+ else
+ $this->fault($e->getMessage());
+ }
+ }
+
+ /**
+ * Generate a SOAP fault message.
+ * @param string message title
+ * @param mixed message details
+ * @param string message code, defalt is 'SERVER'.
+ * @param string actors
+ * @param string message name
+ */
+ public function fault($title, $details='', $code='SERVER', $actor='', $name='')
+ {
+ Prado::trace('SOAP-Fault '.$code. ' '.$title.' : '.$details, 'System.Web.Services.TSoapService');
+ $this->_server->fault($code, $title, $actor, $details, $name);
+ }
+
+ /**
+ * Guess the SOAP method request from the actual SOAP message
+ *
+ * @param string $class current handler class.
+ */
+ protected function guessMethodCallRequested($class)
+ {
+ $namespace = $class.'wsdl';
+ $message = file_get_contents("php://input");
+ $matches= array();
+ if(preg_match('/xmlns:([^=]+)="urn:'.$namespace.'"/', $message, $matches))
+ {
+ if(preg_match('/<'.$matches[1].':([a-zA-Z_]+[a-zA-Z0-9_]+)/', $message, $method))
+ {
+ $this->_requestedMethod = $method[1];
+ }
+ }
+ }
+
+ /**
+ * Soap method guessed from the SOAP message received.
+ * @return string soap method request, null if not found.
+ */
+ public function getRequestedMethod()
+ {
+ return $this->_requestedMethod;
+ }
+
+ /**
+ * Creates the SoapServer instance.
+ * @return SoapServer
+ */
+ protected function createServer()
+ {
+ if($this->_server===null)
+ {
+ if($this->getApplication()->getMode()===TApplicationMode::Debug)
+ ini_set("soap.wsdl_cache_enabled",0);
+ $this->_server = new SoapServer($this->getWsdlUri(),$this->getOptions());
+ }
+ return $this->_server;
+ }
+
+ /**
+ * @return array options for creating SoapServer instance
+ */
+ protected function getOptions()
+ {
+ $options=array();
+ if($this->_version==='1.1')
+ $options['soap_version']=SOAP_1_1;
+ else if($this->_version==='1.2')
+ $options['soap_version']=SOAP_1_2;
+ if(!empty($this->_actor))
+ $options['actor']=$this->_actor;
+ if(!empty($this->_encoding))
+ $options['encoding']=$this->_encoding;
+ if(!empty($this->_uri))
+ $options['uri']=$this->_uri;
+ if(is_string($this->_classMap))
+ {
+ foreach(preg_split('/\s*,\s*/', $this->_classMap) as $className)
+ $options['classmap'][$className]=$className; //complex type uses the class name in the wsdl
+ }
+ return $options;
+ }
+
+ /**
+ * Returns the WSDL content of the SOAP server.
+ * If {@link getWsdlUri WsdlUri} is set, its content will be returned.
+ * If not, the {@link setProvider Provider} class will be investigated
+ * and the WSDL will be automatically genearted.
+ * @return string the WSDL content of the SOAP server
+ */
+ public function getWsdl()
+ {
+ if($this->_wsdlUri==='')
+ {
+ $provider=$this->getProvider();
+ $providerClass=($pos=strrpos($provider,'.'))!==false?substr($provider,$pos+1):$provider;
+ Prado::using($provider);
+ if($this->getApplication()->getMode()===TApplicationMode::Performance && ($cache=$this->getApplication()->getCache())!==null)
+ {
+ $wsdl=$cache->get(self::WSDL_CACHE_PREFIX.$providerClass);
+ if(is_string($wsdl))
+ return $wsdl;
+ Prado::using('System.3rdParty.WsdlGen.WsdlGenerator');
+ $wsdl=WsdlGenerator::generate($providerClass, $this->getUri(), $this->getEncoding());
+ $cache->set(self::WSDL_CACHE_PREFIX.$providerClass,$wsdl);
+ return $wsdl;
+ }
+ else
+ {
+ Prado::using('System.3rdParty.WsdlGen.WsdlGenerator');
+ return WsdlGenerator::generate($providerClass, $this->getUri(), $this->getEncoding());
+ }
+ }
+ else
+ return file_get_contents($this->_wsdlUri);
+ }
+
+ /**
+ * @return string the URI for WSDL
+ */
+ public function getWsdlUri()
+ {
+ if($this->_wsdlUri==='')
+ return $this->getRequest()->getBaseUrl().$this->getService()->constructUrl($this->getID().'.wsdl',false);
+ else
+ return $this->_wsdlUri;
+ }
+
+ /**
+ * @param string the URI for WSDL
+ */
+ public function setWsdlUri($value)
+ {
+ $this->_wsdlUri=$value;
+ }
+
+ /**
+ * @return string the URI for the SOAP service
+ */
+ public function getUri()
+ {
+ if($this->_uri==='')
+ return $this->getRequest()->getBaseUrl().$this->getService()->constructUrl($this->getID(),false);
+ else
+ return $this->_uri;
+ }
+
+ /**
+ * @param string the URI for the SOAP service
+ */
+ public function setUri($uri)
+ {
+ $this->_uri=$uri;
+ }
+
+ /**
+ * @return string the SOAP provider class (in namespace format)
+ */
+ public function getProvider()
+ {
+ return $this->_provider;
+ }
+
+ /**
+ * @param string the SOAP provider class (in namespace format)
+ */
+ public function setProvider($provider)
+ {
+ $this->_provider=$provider;
+ }
+
+ /**
+ * @return string SOAP version, defaults to empty (meaning not set).
+ */
+ public function getVersion()
+ {
+ return $this->_version;
+ }
+
+ /**
+ * @param string SOAP version, either '1.1' or '1.2'
+ * @throws TInvalidDataValueException if neither '1.1' nor '1.2'
+ */
+ public function setVersion($value)
+ {
+ if($value==='1.1' || $value==='1.2' || $value==='')
+ $this->_version=$value;
+ else
+ throw new TInvalidDataValueException('soapserver_version_invalid',$value);
+ }
+
+ /**
+ * @return string actor of the SOAP service
+ */
+ public function getActor()
+ {
+ return $this->_actor;
+ }
+
+ /**
+ * @param string actor of the SOAP service
+ */
+ public function setActor($value)
+ {
+ $this->_actor=$value;
+ }
+
+ /**
+ * @return string encoding of the SOAP service
+ */
+ public function getEncoding()
+ {
+ return $this->_encoding;
+ }
+
+ /**
+ * @param string encoding of the SOAP service
+ */
+ public function setEncoding($value)
+ {
+ $this->_encoding=$value;
+ }
+
+ /**
+ * @return boolean whether the SOAP service is persistent within session. Defaults to false.
+ */
+ public function getSessionPersistent()
+ {
+ return $this->_persistent;
+ }
+
+ /**
+ * @param boolean whether the SOAP service is persistent within session.
+ */
+ public function setSessionPersistent($value)
+ {
+ $this->_persistent=TPropertyValue::ensureBoolean($value);
+ }
+
+ /**
+ * @return string comma delimit list of complex type classes.
+ */
+ public function getClassMaps()
+ {
+ return $this->_classMap;
+ }
+
+ /**
+ * @return string comma delimit list of class names
+ */
+ public function setClassMaps($classes)
+ {
+ $this->_classMap = $classes;
+ }
+} \ No newline at end of file