/**
  * Start a JSON-RPC server, passing the handler class.
  * @param string $service_class
  */
 public function service($service_class)
 {
     $request = new Zend_Json_Server_Request();
     $request->setOptions(array("method" => $this->_request->getParam("method"), "id" => $this->_request->getParam("id"), "params" => $this->_request->getParam("params")));
     $server = new Zend_Json_Server();
     $server->setClass($service_class);
     $server->handle($request);
     exit;
 }
Exemplo n.º 2
0
 /**
  * handle request
  * 
  * @return void
  */
 public function handle()
 {
     try {
         Tinebase_Core::initFramework();
         $exception = FALSE;
     } catch (Exception $exception) {
         if (Tinebase_Core::isLogLevel(Zend_Log::DEBUG)) {
             Tinebase_Core::getLogger()->debug(__METHOD__ . '::' . __LINE__ . ' initFramework exception: ' . $exception);
         }
         // handle all kind of session exceptions as 'Not Authorised'
         if ($exception instanceof Zend_Session_Exception) {
             $exception = new Tinebase_Exception_AccessDenied('Not Authorised', 401);
             // expire session cookie for client
             Zend_Session::expireSessionCookie();
         }
     }
     $server = new Zend_Json_Server();
     $server->setAutoEmitResponse(false);
     $server->setAutoHandleExceptions(false);
     //$server->setUseNamedParams(true);
     $json = file_get_contents('php://input');
     if (substr($json, 0, 1) == '[') {
         if (Tinebase_Core::isLogLevel(Zend_Log::DEBUG)) {
             Tinebase_Core::getLogger()->debug(__METHOD__ . '::' . __LINE__ . ' batched request');
         }
         $isBatchedRequest = true;
         $requests = Zend_Json::decode($json);
     } else {
         $isBatchedRequest = false;
         $requests = array(Zend_Json::decode($json));
     }
     if (Tinebase_Core::isLogLevel(Zend_Log::DEBUG)) {
         $_requests = $requests;
         foreach (array('password', 'oldPassword', 'newPassword') as $field) {
             if (isset($requests[0]["params"][$field])) {
                 $_requests[0]["params"][$field] = "*******";
             }
         }
         if (Tinebase_Core::isLogLevel(Zend_Log::DEBUG)) {
             Tinebase_Core::getLogger()->debug(__METHOD__ . '::' . __LINE__ . ' is JSON request. rawdata: ' . print_r($_requests, true));
         }
     }
     $response = array();
     foreach ($requests as $requestOptions) {
         if ($requestOptions !== NULL) {
             $request = new Zend_Json_Server_Request();
             $request->setOptions($requestOptions);
             $response[] = $exception ? $this->_handleException($server, $request, $exception) : $this->_handle($server, $request);
         } else {
             if (Tinebase_Core::isLogLevel(Zend_Log::NOTICE)) {
                 Tinebase_Core::getLogger()->notice(__METHOD__ . '::' . __LINE__ . ' Got empty request options: skip request.');
             }
             $response[] = NULL;
         }
     }
     echo $isBatchedRequest ? '[' . implode(',', $response) . ']' : $response[0];
 }
 /**
  * (non-PHPdoc)
  * @see Tinebase_Server_Interface::handle()
  */
 public function handle(\Zend\Http\Request $request = null, $body = null)
 {
     $this->_request = $request instanceof \Zend\Http\Request ? $request : Tinebase_Core::get(Tinebase_Core::REQUEST);
     $this->_body = $body !== null ? $body : fopen('php://input', 'r');
     $request = $request instanceof \Zend\Http\Request ? $request : new \Zend\Http\PhpEnvironment\Request();
     // only for debugging
     //Tinebase_Core::getLogger()->DEBUG(__METHOD__ . '::' . __LINE__ . " raw request: " . $request->__toString());
     // handle CORS requests
     if ($request->getHeaders()->has('ORIGIN') && !$request->getHeaders()->has('X-FORWARDED-HOST')) {
         /**
          * First the client sends a preflight request
          * 
          * METHOD: OPTIONS
          * Access-Control-Request-Headers:x-requested-with, content-type
          * Access-Control-Request-Method:POST
          * Origin:http://other.site
          * Referer:http://other.site/example.html
          * User-Agent:Mozilla/5.0 (X11; Linux x86_64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/38.0.2125.111 Safari/537.36
          * 
          * We have to respond with
          * 
          * Access-Control-Allow-Credentials:true
          * Access-Control-Allow-Headers:x-requested-with, x-tine20-request-type, content-type, x-tine20-jsonkey
          * Access-Control-Allow-Methods:POST
          * Access-Control-Allow-Origin:http://other.site
          * 
          * Then the client sends the standard JSON request with two additional headers
          * 
          * METHOD: POST
          * Origin:http://other.site
          * Referer:http://other.site/example.html
          * Standard-JSON-Rquest-Headers...
          * 
          * We have to add two additional headers to our standard response
          * 
          * Access-Control-Allow-Credentials:true
          * Access-Control-Allow-Origin:http://other.site
          */
         $origin = $request->getHeaders('ORIGIN')->getFieldValue();
         $uri = \Zend\Uri\UriFactory::factory($origin);
         if (in_array($uri->getScheme(), array('http', 'https'))) {
             $allowedOrigins = array_merge((array) Tinebase_Core::getConfig()->get(Tinebase_Config::ALLOWEDJSONORIGINS, array()), array($this->_request->getServer('SERVER_NAME')));
             if (in_array($uri->getHost(), $allowedOrigins)) {
                 // this headers have to be sent, for any CORS'ed JSON request
                 header('Access-Control-Allow-Origin: ' . $origin);
                 header('Access-Control-Allow-Credentials: true');
             }
             // check for CORS preflight request
             if ($request->getMethod() == \Zend\Http\Request::METHOD_OPTIONS && $request->getHeaders()->has('ACCESS-CONTROL-REQUEST-METHOD')) {
                 $this->_methods = array('handleCors');
                 if (in_array($uri->getHost(), $allowedOrigins)) {
                     header('Access-Control-Allow-Methods: POST');
                     header('Access-Control-Allow-Headers: x-requested-with, x-tine20-request-type, content-type, x-tine20-jsonkey');
                     header('Access-Control-Max-Age: 3600');
                     // cache result of OPTIONS request for 1 hour
                 } else {
                     Tinebase_Core::getLogger()->WARN(__METHOD__ . '::' . __LINE__ . " unhandled CORS preflight request from {$origin}");
                     Tinebase_Core::getLogger()->INFO(__METHOD__ . '::' . __LINE__ . " you may want to set \"'allowedJsonOrigins' => array('{$uri->getHost()}'),\" to config.inc.php");
                     Tinebase_Core::getLogger()->DEBUG(__METHOD__ . '::' . __LINE__ . " allowed origins: " . print_r($allowedOrigins, TRUE));
                 }
                 // stop further processing => is OPTIONS request
                 return;
             }
         }
     }
     $exception = false;
     if (Tinebase_Session::sessionExists()) {
         try {
             Tinebase_Core::startCoreSession();
         } catch (Zend_Session_Exception $zse) {
             $exception = new Tinebase_Exception_AccessDenied('Not Authorised', 401);
             // expire session cookie for client
             Tinebase_Session::expireSessionCookie();
         }
     }
     if ($exception === false) {
         try {
             Tinebase_Core::initFramework();
         } catch (Exception $exception) {
             if (Tinebase_Core::isLogLevel(Zend_Log::DEBUG)) {
                 Tinebase_Core::getLogger()->debug(__METHOD__ . '::' . __LINE__ . ' initFramework exception: ' . $exception);
             }
         }
     }
     $json = $request->getContent();
     $json = Tinebase_Core::filterInputForDatabase($json);
     if (substr($json, 0, 1) == '[') {
         if (Tinebase_Core::isLogLevel(Zend_Log::DEBUG)) {
             Tinebase_Core::getLogger()->debug(__METHOD__ . '::' . __LINE__ . ' batched request');
         }
         $isBatchedRequest = true;
         $requests = Zend_Json::decode($json);
     } else {
         $isBatchedRequest = false;
         $requests = array(Zend_Json::decode($json));
     }
     if (Tinebase_Core::isLogLevel(Zend_Log::DEBUG)) {
         $_requests = $requests;
         foreach (array('password', 'oldPassword', 'newPassword') as $field) {
             if (isset($requests[0]["params"][$field])) {
                 $_requests[0]["params"][$field] = "*******";
             }
         }
         if (Tinebase_Core::isLogLevel(Zend_Log::DEBUG)) {
             Tinebase_Core::getLogger()->debug(__METHOD__ . '::' . __LINE__ . ' is JSON request. rawdata: ' . print_r($_requests, true));
         }
     }
     $response = array();
     foreach ($requests as $requestOptions) {
         if ($requestOptions !== NULL) {
             $request = new Zend_Json_Server_Request();
             $request->setOptions($requestOptions);
             $response[] = $exception ? $this->_handleException($request, $exception) : $this->_handle($request);
         } else {
             if (Tinebase_Core::isLogLevel(Zend_Log::NOTICE)) {
                 Tinebase_Core::getLogger()->notice(__METHOD__ . '::' . __LINE__ . ' Got empty request options: skip request.');
             }
             $response[] = NULL;
         }
     }
     if (!headers_sent()) {
         header('Content-type: application/json');
     }
     echo $isBatchedRequest ? '[' . implode(',', $response) . ']' : $response[0];
 }