Current File : /home/k/a/r/karenpetzb/www/items/category/Server.php.tar
home/karenpetzb/library/Zend/Rest/Server.php000060400000044767150714227220015121 0ustar00<?php
/**
 * Zend Framework
 *
 * LICENSE
 *
 * This source file is subject to the new BSD license that is bundled
 * with this package in the file LICENSE.txt.
 * It is also available through the world-wide-web at this URL:
 * http://framework.zend.com/license/new-bsd
 * If you did not receive a copy of the license and are unable to
 * obtain it through the world-wide-web, please send an email
 * to license@zend.com so we can send you a copy immediately.
 *
 * @category   Zend
 * @package    Zend_Rest
 * @subpackage Server
 * @copyright  Copyright (c) 2005-2008 Zend Technologies USA Inc. (http://www.zend.com)
 * @license    http://framework.zend.com/license/new-bsd     New BSD License
 */

/**
 * Zend_Server_Interface
 */
require_once 'Zend/Server/Interface.php';

/**
 * Zend_Server_Reflection
 */
require_once 'Zend/Server/Reflection.php';

/**
 * Zend_Rest_Server_Exception
 */
require_once 'Zend/Rest/Server/Exception.php';

/**
 * Zend_Server_Abstract
 */
require_once 'Zend/Server/Abstract.php';

/**
 * @category   Zend
 * @package    Zend_Rest
 * @subpackage Server
 * @copyright  Copyright (c) 2005-2008 Zend Technologies USA Inc. (http://www.zend.com)
 * @license    http://framework.zend.com/license/new-bsd     New BSD License
 */
class Zend_Rest_Server implements Zend_Server_Interface
{
    /**
     * Class Constructor Args
     * @var array
     */
    protected $_args = array();

    /**
     * @var string Encoding
     */
    protected $_encoding = 'UTF-8';

    /**
     * @var array An array of Zend_Server_Reflect_Method
     */
    protected $_functions = array();

    /**
     * @var array Array of headers to send
     */
    protected $_headers = array();

    /**
     * @var array PHP's Magic Methods, these are ignored
     */
    protected static $magicMethods = array(
        '__construct',
        '__destruct',
        '__get',
        '__set',
        '__call',
        '__sleep',
        '__wakeup',
        '__isset',
        '__unset',
        '__tostring',
        '__clone',
        '__set_state',
    );

    /**
     * @var string Current Method
     */
    protected $_method;

    /**
     * @var Zend_Server_Reflection
     */
    protected $_reflection = null;

    /**
     * Whether or not {@link handle()} should send output or return the response.
     * @var boolean Defaults to false
     */
    protected $_returnResponse = false;

    /**
     * Constructor
     */
    public function __construct()
    {
        set_exception_handler(array($this, "fault"));
        $this->_reflection = new Zend_Server_Reflection();
    }

    /**
     * Set XML encoding
     * 
     * @param  string $encoding 
     * @return Zend_Rest_Server
     */
    public function setEncoding($encoding)
    {
        $this->_encoding = (string) $encoding;
        return $this;
    }

    /**
     * Get XML encoding
     * 
     * @return string
     */
    public function getEncoding()
    {
        return $this->_encoding;
    }

    /**
     * Lowercase a string
     *
     * Lowercase's a string by reference
     *
     * @param string $value
     * @param string $key
     * @return string Lower cased string
     */
    public static function lowerCase(&$value, &$key)
    {
        return $value = strtolower($value);
    }

    /**
     * Whether or not to return a response
     *
     * If called without arguments, returns the value of the flag. If called
     * with an argument, sets the flag.
     *
     * When 'return response' is true, {@link handle()} will not send output,
     * but will instead return the response from the dispatched function/method.
     *
     * @param boolean $flag
     * @return boolean|Zend_Rest_Server Returns Zend_Rest_Server when used to set the flag; returns boolean flag value otherwise.
     */
    public function returnResponse($flag = null)
    {
        if (null == $flag) {
            return $this->_returnResponse;
        }

        $this->_returnResponse = ($flag) ? true : false;
        return $this;
    }

    /**
     * Implement Zend_Server_Interface::handle()
     *
     * @param  array $request
     * @throws Zend_Rest_Server_Exception
     * @return string|void
     */
    public function handle($request = false)
    {
        $this->_headers = array('Content-Type: text/xml');
        if (!$request) {
            $request = $_REQUEST;
        }
        if (isset($request['method'])) {
            $this->_method = $request['method'];
            if (isset($this->_functions[$this->_method])) {
                if ($this->_functions[$this->_method] instanceof Zend_Server_Reflection_Function || $this->_functions[$this->_method] instanceof Zend_Server_Reflection_Method && $this->_functions[$this->_method]->isPublic()) {
                    $request_keys = array_keys($request);
                    array_walk($request_keys, array(__CLASS__, "lowerCase"));
                    $request = array_combine($request_keys, $request);

                    $func_args = $this->_functions[$this->_method]->getParameters();

                    $calling_args = array();
                    foreach ($func_args as $arg) {
                        if (isset($request[strtolower($arg->getName())])) {
                            $calling_args[] = $request[strtolower($arg->getName())];
                        } elseif ($arg->isOptional()) {
                            $calling_args[] = $arg->getDefaultValue();
                        }
                    }

                    foreach ($request as $key => $value) {
                        if (substr($key, 0, 3) == 'arg') {
                            $key = str_replace('arg', '', $key);
                            $calling_args[$key] = $value;
                        }
                    }

                    // Sort arguments by key -- @see ZF-2279
                    ksort($calling_args);

                    $result = false;
                    if (count($calling_args) < count($func_args)) {
                        $result = $this->fault(new Zend_Rest_Server_Exception('Invalid Method Call to ' . $this->_method . '. Requires ' . count($func_args) . ', ' . count($calling_args) . ' given.'), 400);
                    }

                    if (!$result && $this->_functions[$this->_method] instanceof Zend_Server_Reflection_Method) {
                        // Get class
                        $class = $this->_functions[$this->_method]->getDeclaringClass()->getName();

                        if ($this->_functions[$this->_method]->isStatic()) {
                            // for some reason, invokeArgs() does not work the same as
                            // invoke(), and expects the first argument to be an object.
                            // So, using a callback if the method is static.
                            $result = $this->_callStaticMethod($class, $calling_args);
                        } else {
                            // Object method
                            $result = $this->_callObjectMethod($class, $calling_args);
                        }
                    } elseif (!$result) {
                        try {
                            $result = call_user_func_array($this->_functions[$this->_method]->getName(), $calling_args); //$this->_functions[$this->_method]->invokeArgs($calling_args);
                        } catch (Exception $e) {
                            $result = $this->fault($e);
                        }
                    }
                } else {
                    require_once "Zend/Rest/Server/Exception.php";
                    $result = $this->fault(
                        new Zend_Rest_Server_Exception("Unknown Method '$this->_method'."),
                        404
                    );
                }
            } else {
                require_once "Zend/Rest/Server/Exception.php";
                $result = $this->fault(
                    new Zend_Rest_Server_Exception("Unknown Method '$this->_method'."),
                    404
                );
            }
        } else {
            require_once "Zend/Rest/Server/Exception.php";
            $result = $this->fault(
                new Zend_Rest_Server_Exception("No Method Specified."),
                404
            );
        }

        if ($result instanceof SimpleXMLElement) {
            $response = $result->asXML();
        } elseif ($result instanceof DOMDocument) {
            $response = $result->saveXML();
        } elseif ($result instanceof DOMNode) {
            $response = $result->ownerDocument->saveXML($result);
        } elseif (is_array($result) || is_object($result)) {
            $response = $this->_handleStruct($result);
        } else {
            $response = $this->_handleScalar($result);
        }

        if (!$this->returnResponse()) {
            if (!headers_sent()) {
                foreach ($this->_headers as $header) {
                    header($header);
                }
            }

            echo $response;
            return;
        }

        return $response;
     }

    /**
     * Implement Zend_Server_Interface::setClass()
     *
     * @param string $classname Class name
     * @param string $namespace Class namespace (unused)
     * @param array $argv An array of Constructor Arguments
     */
    public function setClass($classname, $namespace = '', $argv = array())
    {
        $this->_args = $argv;
        foreach ($this->_reflection->reflectClass($classname, $argv)->getMethods() as $method) {
            $this->_functions[$method->getName()] = $method;
        }
    }

    /**
     * Handle an array or object result
     *
     * @param array|object $struct Result Value
     * @return string XML Response
     */
    protected function _handleStruct($struct)
    {
        $function = $this->_functions[$this->_method];
        if ($function instanceof Zend_Server_Reflection_Method) {
            $class = $function->getDeclaringClass()->getName();
        } else {
            $class = false;
        }

        $method = $function->getName();

        $dom    = new DOMDocument('1.0', $this->getEncoding());
        if ($class) {
            $root   = $dom->createElement($class);
            $method = $dom->createElement($method);
            $root->appendChild($method);
        } else {
            $root   = $dom->createElement($method);
            $method = $root;
        }
        $root->setAttribute('generator', 'zend');
        $root->setAttribute('version', '1.0');
        $dom->appendChild($root);

        $this->_structValue($struct, $dom, $method);

        $struct = (array) $struct;
        if (!isset($struct['status'])) {
            $status = $dom->createElement('status', 'success');
            $method->appendChild($status);
        }

        return $dom->saveXML();
    }

    /**
     * Recursively iterate through a struct
     *
     * Recursively iterates through an associative array or object's properties
     * to build XML response.
     *
     * @param mixed $struct
     * @param DOMDocument $dom
     * @param DOMElement $parent
     * @return void
     */
    protected function _structValue($struct, DOMDocument $dom, DOMElement $parent)
    {
        $struct = (array) $struct;

        foreach ($struct as $key => $value) {
            if ($value === false) {
                $value = 0;
            } elseif ($value === true) {
                $value = 1;
            }

            if (ctype_digit((string) $key)) {
                $key = 'key_' . $key;
            }

            if (is_array($value) || is_object($value)) {
                $element = $dom->createElement($key);
                $this->_structValue($value, $dom, $element);
            } else {
                $element = $dom->createElement($key);
                $element->appendChild($dom->createTextNode($value));
            }

            $parent->appendChild($element);
        }
    }

    /**
     * Handle a single value
     *
     * @param string|int|boolean $value Result value
     * @return string XML Response
     */
    protected function _handleScalar($value)
    {
        $function = $this->_functions[$this->_method];
        if ($function instanceof Zend_Server_Reflection_Method) {
            $class = $function->getDeclaringClass()->getName();
        } else {
            $class = false;
        }

        $method = $function->getName();

        $dom = new DOMDocument('1.0', $this->getEncoding());
        if ($class) {
            $xml = $dom->createElement($class);
            $methodNode = $dom->createElement($method);
            $xml->appendChild($methodNode);
        } else {
            $xml = $dom->createElement($method);
            $methodNode = $xml;
        }
        $xml->setAttribute('generator', 'zend');
        $xml->setAttribute('version', '1.0');
        $dom->appendChild($xml);

        if ($value === false) {
            $value = 0;
        } elseif ($value === true) {
            $value = 1;
        }

        if (isset($value)) {
            $element = $dom->createElement('response');
            $element->appendChild($dom->createTextNode($value));
            $methodNode->appendChild($element);
        } else {
            $methodNode->appendChild($dom->createElement('response'));
        }

        $methodNode->appendChild($dom->createElement('status', 'success'));

        return $dom->saveXML();
    }

    /**
     * Implement Zend_Server_Interface::fault()
     *
     * Creates XML error response, returning DOMDocument with response.
     *
     * @param string|Exception $fault Message
     * @param int $code Error Code
     * @return DOMDocument
     */
    public function fault($exception = null, $code = null)
    {
        if (isset($this->_functions[$this->_method])) {
            $function = $this->_functions[$this->_method];
        } elseif (isset($this->_method)) {
            $function = $this->_method;
        } else {
            $function = 'rest';
        }

        if ($function instanceof Zend_Server_Reflection_Method) {
            $class = $function->getDeclaringClass()->getName();
        } else {
            $class = false;
        }

        if ($function instanceof Zend_Server_Reflection_Function_Abstract) {
            $method = $function->getName();
        } else {
            $method = $function;
        }

        $dom = new DOMDocument('1.0', $this->getEncoding());
        if ($class) {
            $xml       = $dom->createElement($class);
            $xmlMethod = $dom->createElement($method);
            $xml->appendChild($xmlMethod);
        } else {
            $xml       = $dom->createElement($method);
            $xmlMethod = $xml;
        }
        $xml->setAttribute('generator', 'zend');
        $xml->setAttribute('version', '1.0');
        $dom->appendChild($xml);

        $xmlResponse = $dom->createElement('response');
        $xmlMethod->appendChild($xmlResponse);

        if ($exception instanceof Exception) {
            $element = $dom->createElement('message');
            $element->appendChild($dom->createTextNode($exception->getMessage()));
            $xmlResponse->appendChild($element);
            $code = $exception->getCode();
        } elseif (!is_null($exception) || 'rest' == $function) {
            $xmlResponse->appendChild($dom->createElement('message', 'An unknown error occured. Please try again.'));
        } else {
            $xmlResponse->appendChild($dom->createElement('message', 'Call to ' . $method . ' failed.'));
        }

        $xmlMethod->appendChild($xmlResponse);
        $xmlMethod->appendChild($dom->createElement('status', 'failed'));

        // Headers to send
        if (is_null($code) || (404 != $code))
        {
            $this->_headers[] = 'HTTP/1.0 400 Bad Request';
        } else {
            $this->_headers[] = 'HTTP/1.0 404 File Not Found';
        }

        return $dom;
    }

    /**
     * Retrieve any HTTP extra headers set by the server
     *
     * @return array
     */
    public function getHeaders()
    {
        return $this->_headers;
    }

    /**
     * Implement Zend_Server_Interface::addFunction()
     *
     * @param string $function Function Name
     * @param string $namespace Function namespace (unused)
     */
    public function addFunction($function, $namespace = '')
    {
        if (!is_array($function)) {
            $function = (array) $function;
        }

        foreach ($function as $func) {
            if (is_callable($func) && !in_array($func, self::$magicMethods)) {
                $this->_functions[$func] = $this->_reflection->reflectFunction($func);
            } else {
                throw new Zend_Rest_Server_Exception("Invalid Method Added to Service.");
            }
        }
    }

    /**
     * Implement Zend_Server_Interface::getFunctions()
     *
     * @return array An array of Zend_Server_Reflection_Method's
     */
    public function getFunctions()
    {
        return $this->_functions;
    }

    /**
     * Implement Zend_Server_Interface::loadFunctions()
     *
     * @todo Implement
     * @param array $functions
     */
    public function loadFunctions($functions)
    {
    }

    /**
     * Implement Zend_Server_Interface::setPersistence()
     *
     * @todo Implement
     * @param int $mode
     */
    public function setPersistence($mode)
    {
    }

    /**
     * Call a static class method and return the result
     * 
     * @param  string $class 
     * @param  array $args 
     * @return mixed
     */
    protected function _callStaticMethod($class, array $args)
    {
        try {
            $result = call_user_func_array(array($class, $this->_functions[$this->_method]->getName()), $args);
        } catch (Exception $e) {
            $result = $this->fault($e);
        }
        return $result;
    }

    /**
     * Call an instance method of an object
     * 
     * @param  string $class
     * @param  array $args
     * @return mixed
     * @throws Zend_Rest_Server_Exception For invalid class name
     */
    protected function _callObjectMethod($class, array $args)
    {
        try {
            if ($this->_functions[$this->_method]->getDeclaringClass()->getConstructor()) {
                $object = $this->_functions[$this->_method]->getDeclaringClass()->newInstanceArgs($this->_args);
            } else {
                $object = $this->_functions[$this->_method]->getDeclaringClass()->newInstance();
            }
        } catch (Exception $e) {
            echo $e->getMessage();
            throw new Zend_Rest_Server_Exception('Error instantiating class ' . $class . ' to invoke method ' . $this->_functions[$this->_method]->getName(), 500);
        }

        try {
            $result = $this->_functions[$this->_method]->invokeArgs($object, $args);
        } catch (Exception $e) {
            $result = $this->fault($e);
        }

        return $result;
    }
}
home/karenpetzb/library/Zend/XmlRpc/Server.php000060400000040376150715305120015376 0ustar00<?php
/**
 * Zend Framework
 *
 * LICENSE
 *
 * This source file is subject to the new BSD license that is bundled
 * with this package in the file LICENSE.txt.
 * It is also available through the world-wide-web at this URL:
 * http://framework.zend.com/license/new-bsd
 * If you did not receive a copy of the license and are unable to
 * obtain it through the world-wide-web, please send an email
 * to license@zend.com so we can send you a copy immediately.
 *
 * @category   Zend
 * @package    Zend_XmlRpc
 * @subpackage Server
 * @copyright  Copyright (c) 2005-2008 Zend Technologies USA Inc. (http://www.zend.com)
 * @license    http://framework.zend.com/license/new-bsd     New BSD License
 * @version    $Id: Server.php 12195 2008-10-30 13:34:35Z matthew $
 */

/**
 * Extends Zend_Server_Abstract
 */
require_once 'Zend/Server/Abstract.php';

/**
 * Exception this class throws
 */
require_once 'Zend/XmlRpc/Server/Exception.php';

/**
 * XMLRPC Request
 */
require_once 'Zend/XmlRpc/Request.php';

/**
 * XMLRPC Response
 */
require_once 'Zend/XmlRpc/Response.php';

/**
 * XMLRPC HTTP Response
 */
require_once 'Zend/XmlRpc/Response/Http.php';

/**
 * XMLRPC server fault class
 */
require_once 'Zend/XmlRpc/Server/Fault.php';

/**
 * XMLRPC server system methods class
 */
require_once 'Zend/XmlRpc/Server/System.php';

/**
 * Convert PHP to and from xmlrpc native types
 */
require_once 'Zend/XmlRpc/Value.php';

/**
 * Reflection API for function/method introspection
 */
require_once 'Zend/Server/Reflection.php';

/**
 * Zend_Server_Reflection_Function_Abstract
 */
require_once 'Zend/Server/Reflection/Function/Abstract.php';

/**
 * Specifically grab the Zend_Server_Reflection_Method for manually setting up
 * system.* methods and handling callbacks in {@link loadFunctions()}.
 */
require_once 'Zend/Server/Reflection/Method.php';

/**
 * An XML-RPC server implementation
 *
 * Example:
 * <code>
 * require_once 'Zend/XmlRpc/Server.php';
 * require_once 'Zend/XmlRpc/Server/Cache.php';
 * require_once 'Zend/XmlRpc/Server/Fault.php';
 * require_once 'My/Exception.php';
 * require_once 'My/Fault/Observer.php';
 *
 * // Instantiate server
 * $server = new Zend_XmlRpc_Server();
 *
 * // Allow some exceptions to report as fault responses:
 * Zend_XmlRpc_Server_Fault::attachFaultException('My_Exception');
 * Zend_XmlRpc_Server_Fault::attachObserver('My_Fault_Observer');
 *
 * // Get or build dispatch table:
 * if (!Zend_XmlRpc_Server_Cache::get($filename, $server)) {
 *     require_once 'Some/Service/Class.php';
 *     require_once 'Another/Service/Class.php';
 *
 *     // Attach Some_Service_Class in 'some' namespace
 *     $server->setClass('Some_Service_Class', 'some');
 *
 *     // Attach Another_Service_Class in 'another' namespace
 *     $server->setClass('Another_Service_Class', 'another');
 *
 *     // Create dispatch table cache file
 *     Zend_XmlRpc_Server_Cache::save($filename, $server);
 * }
 *
 * $response = $server->handle();
 * echo $response;
 * </code>
 *
 * @category   Zend
 * @package    Zend_XmlRpc
 * @subpackage Server
 * @copyright  Copyright (c) 2005-2008 Zend Technologies USA Inc. (http://www.zend.com)
 * @license    http://framework.zend.com/license/new-bsd     New BSD License
 */
class Zend_XmlRpc_Server extends Zend_Server_Abstract
{
    /**
     * Character encoding
     * @var string
     */
    protected $_encoding = 'UTF-8';

    /**
     * Request processed
     * @var null|Zend_XmlRpc_Request
     */
    protected $_request = null;

    /**
     * Class to use for responses; defaults to {@link Zend_XmlRpc_Response_Http}
     * @var string
     */
    protected $_responseClass = 'Zend_XmlRpc_Response_Http';

    /**
     * Dispatch table of name => method pairs
     * @var Zend_XmlRpc_Server_ServerDefinition
     */
    protected $_table;

    /**
     * PHP types => XML-RPC types
     * @var array
     */
    protected $_typeMap = array(
        'i4'               => 'i4',
        'int'              => 'int',
        'integer'          => 'int',
        'double'           => 'double',
        'float'            => 'double',
        'real'             => 'double',
        'boolean'          => 'boolean',
        'bool'             => 'boolean',
        'true'             => 'boolean',
        'false'            => 'boolean',
        'string'           => 'string',
        'str'              => 'string',
        'base64'           => 'base64',
        'dateTime.iso8601' => 'dateTime.iso8601',
        'date'             => 'dateTime.iso8601',
        'time'             => 'dateTime.iso8601',
        'time'             => 'dateTime.iso8601',
        'array'            => 'array',
        'struct'           => 'struct',
        'null'             => 'nil',
        'nil'              => 'nil',
        'void'             => 'void',
        'mixed'            => 'struct'
    );

    /**
     * Constructor
     *
     * Creates system.* methods.
     *
     * @return void
     */
    public function __construct()
    {
        $this->_table = new Zend_Server_Definition();
        $this->_registerSystemMethods();
    }

    /**
     * Proxy calls to system object
     * 
     * @param  string $method 
     * @param  array $params 
     * @return mixed
     * @throws Zend_XmlRpc_Server_Exception
     */
    public function __call($method, $params)
    {
        $system = $this->getSystem();
        if (!method_exists($system, $method)) {
            throw new Zend_XmlRpc_Server_Exception('Unknown instance method called on server: ' . $method);
        }
        return call_user_func_array(array($system, $method), $params);
    }

    /**
     * Attach a callback as an XMLRPC method
     *
     * Attaches a callback as an XMLRPC method, prefixing the XMLRPC method name
     * with $namespace, if provided. Reflection is done on the callback's
     * docblock to create the methodHelp for the XMLRPC method.
     *
     * Additional arguments to pass to the function at dispatch may be passed;
     * any arguments following the namespace will be aggregated and passed at
     * dispatch time.
     *
     * @param string|array $function Valid callback
     * @param string $namespace Optional namespace prefix
     * @return void
     * @throws Zend_XmlRpc_Server_Exception
     */
    public function addFunction($function, $namespace = '')
    {
        if (!is_string($function) && !is_array($function)) {
            throw new Zend_XmlRpc_Server_Exception('Unable to attach function; invalid', 611);
        }

        $argv = null;
        if (2 < func_num_args()) {
            $argv = func_get_args();
            $argv = array_slice($argv, 2);
        }

        $function = (array) $function;
        foreach ($function as $func) {
            if (!is_string($func) || !function_exists($func)) {
                throw new Zend_XmlRpc_Server_Exception('Unable to attach function; invalid', 611);
            }
            $reflection = Zend_Server_Reflection::reflectFunction($func, $argv, $namespace);
            $this->_buildSignature($reflection);
        }
    }

    /**
     * Attach class methods as XMLRPC method handlers
     *
     * $class may be either a class name or an object. Reflection is done on the
     * class or object to determine the available public methods, and each is
     * attached to the server as an available method; if a $namespace has been
     * provided, that namespace is used to prefix the XMLRPC method names.
     *
     * Any additional arguments beyond $namespace will be passed to a method at
     * invocation.
     *
     * @param string|object $class
     * @param string $namespace Optional
     * @param mixed $argv Optional arguments to pass to methods
     * @return void
     * @throws Zend_XmlRpc_Server_Exception on invalid input
     */
    public function setClass($class, $namespace = '', $argv = null)
    {
        if (is_string($class) && !class_exists($class)) {
            if (!class_exists($class)) {
                throw new Zend_XmlRpc_Server_Exception('Invalid method class', 610);
            }
        }

        $argv = null;
        if (3 < func_num_args()) {
            $argv = func_get_args();
            $argv = array_slice($argv, 3);
        }

        $dispatchable = Zend_Server_Reflection::reflectClass($class, $argv, $namespace);
        foreach ($dispatchable->getMethods() as $reflection) {
            $this->_buildSignature($reflection, $class);
        }
    }

    /**
     * Raise an xmlrpc server fault
     *
     * @param string|Exception $fault
     * @param int $code
     * @return Zend_XmlRpc_Server_Fault
     */
    public function fault($fault = null, $code = 404)
    {
        if (!$fault instanceof Exception) {
            $fault = (string) $fault;
            if (empty($fault)) {
                $fault = 'Unknown error';
            }
            $fault = new Zend_XmlRpc_Server_Exception($fault, $code);
        }

        return Zend_XmlRpc_Server_Fault::getInstance($fault);
    }

    /**
     * Handle an xmlrpc call
     *
     * @param Zend_XmlRpc_Request $request Optional
     * @return Zend_XmlRpc_Response|Zend_XmlRpc_Fault
     */
    public function handle($request = false)
    {
        // Get request
        if ((!$request || !$request instanceof Zend_XmlRpc_Request)
            && (null === ($request = $this->getRequest()))
        ) {
            require_once 'Zend/XmlRpc/Request/Http.php';
            $request = new Zend_XmlRpc_Request_Http();
            $request->setEncoding($this->getEncoding());
        }

        $this->setRequest($request);

        if ($request->isFault()) {
            $response = $request->getFault();
        } else {
            try {
                $response = $this->_handle($request);
            } catch (Exception $e) {
                $response = $this->fault($e);
            }
        }

        // Set output encoding
        $response->setEncoding($this->getEncoding());

        return $response;
    }

    /**
     * Load methods as returned from {@link getFunctions}
     *
     * Typically, you will not use this method; it will be called using the
     * results pulled from {@link Zend_XmlRpc_Server_Cache::get()}.
     *
     * @param  array|Zend_Server_Definition $definition
     * @return void
     * @throws Zend_XmlRpc_Server_Exception on invalid input
     */
    public function loadFunctions($definition)
    {
        if (!is_array($definition) && (!$definition instanceof Zend_Server_Definition)) {
            if (is_object($definition)) {
                $type = get_class($definition);
            } else {
                $type = gettype($definition);
            }
            throw new Zend_XmlRpc_Server_Exception('Unable to load server definition; must be an array or Zend_Server_Definition, received ' . $type, 612);
        }

        $this->_table->clearMethods();
        $this->_registerSystemMethods();

        if ($definition instanceof Zend_Server_Definition) {
            $definition = $definition->getMethods();
        }

        foreach ($definition as $key => $method) {
            if ('system.' == substr($key, 0, 7)) {
                continue;
            }
            $this->_table->addMethod($method, $key);
        }
    }

    /**
     * Set encoding
     *
     * @param string $encoding
     * @return Zend_XmlRpc_Server
     */
    public function setEncoding($encoding)
    {
        $this->_encoding = $encoding;
        return $this;
    }

    /**
     * Retrieve current encoding
     *
     * @return string
     */
    public function getEncoding()
    {
        return $this->_encoding;
    }

    /**
     * Do nothing; persistence is handled via {@link Zend_XmlRpc_Server_Cache}
     *
     * @param  mixed $mode
     * @return void
     */
    public function setPersistence($mode)
    {
    }

    /**
     * Set the request object
     *
     * @param string|Zend_XmlRpc_Request $request
     * @return Zend_XmlRpc_Server
     * @throws Zend_XmlRpc_Server_Exception on invalid request class or object
     */
    public function setRequest($request)
    {
        if (is_string($request) && class_exists($request)) {
            $request = new $request();
            if (!$request instanceof Zend_XmlRpc_Request) {
                throw new Zend_XmlRpc_Server_Exception('Invalid request class');
            }
            $request->setEncoding($this->getEncoding());
        } elseif (!$request instanceof Zend_XmlRpc_Request) {
            throw new Zend_XmlRpc_Server_Exception('Invalid request object');
        }

        $this->_request = $request;
        return $this;
    }

    /**
     * Return currently registered request object
     *
     * @return null|Zend_XmlRpc_Request
     */
    public function getRequest()
    {
        return $this->_request;
    }

    /**
     * Set the class to use for the response
     *
     * @param string $class
     * @return boolean True if class was set, false if not
     */
    public function setResponseClass($class)
    {
        if (class_exists($class)) {
            $reflection = new ReflectionClass($class);
            if ($reflection->isSubclassOf(new ReflectionClass('Zend_XmlRpc_Response'))) {
                $this->_responseClass = $class;
                return true;
            }
        }

        return false;
    }

    /**
     * Retrieve current response class
     * 
     * @return string
     */
    public function getResponseClass()
    {
        return $this->_responseClass;
    }

    /**
     * Retrieve dispatch table
     * 
     * @return array
     */
    public function getDispatchTable()
    {
        return $this->_table;
    }

    /**
     * Returns a list of registered methods
     *
     * Returns an array of dispatchables (Zend_Server_Reflection_Function,
     * _Method, and _Class items).
     *
     * @return array
     */
    public function getFunctions()
    {
        return $this->_table->toArray();
    }

    /**
     * Retrieve system object
     * 
     * @return Zend_XmlRpc_Server_System
     */
    public function getSystem()
    {
        return $this->_system;
    }

    /**
     * Map PHP type to XML-RPC type
     * 
     * @param  string $type 
     * @return string
     */
    protected function _fixType($type)
    {
        if (isset($this->_typeMap[$type])) {
            return $this->_typeMap[$type];
        }
        return 'void';
    }

    /**
     * Handle an xmlrpc call (actual work)
     *
     * @param Zend_XmlRpc_Request $request
     * @return Zend_XmlRpc_Response
     * @throws Zend_XmlRpcServer_Exception|Exception
     * Zend_XmlRpcServer_Exceptions are thrown for internal errors; otherwise,
     * any other exception may be thrown by the callback
     */
    protected function _handle(Zend_XmlRpc_Request $request)
    {
        $method = $request->getMethod();

        // Check for valid method
        if (!$this->_table->hasMethod($method)) {
            throw new Zend_XmlRpc_Server_Exception('Method "' . $method . '" does not exist', 620);
        }

        $info     = $this->_table->getMethod($method);
        $params   = $request->getParams();
        $argv     = $info->getInvokeArguments();
        if (0 < count($argv)) {
            $params = array_merge($params, $argv);
        }

        // Check calling parameters against signatures
        $matched    = false;
        $sigCalled  = $request->getTypes();

        $sigLength  = count($sigCalled);
        $paramsLen  = count($params);
        if ($sigLength < $paramsLen) {
            for ($i = $sigLength; $i < $paramsLen; ++$i) {
                $xmlRpcValue = Zend_XmlRpc_Value::getXmlRpcValue($params[$i]);
                $sigCalled[] = $xmlRpcValue->getType();
            }
        }

        $signatures = $info->getPrototypes();
        foreach ($signatures as $signature) {
            $sigParams = $signature->getParameters();
            if ($sigCalled === $sigParams) {
                $matched = true;
                break;
            }
        }
        if (!$matched) {
            throw new Zend_XmlRpc_Server_Exception('Calling parameters do not match signature', 623);
        }

        $return        = $this->_dispatch($info, $params);
        $responseClass = $this->getResponseClass();
        return new $responseClass($return);
    }

    /**
     * Register system methods with the server
     * 
     * @return void
     */
    protected function _registerSystemMethods()
    {
        $system = new Zend_XmlRpc_Server_System($this);
        $this->_system = $system;
        $this->setClass($system, 'system');
    }
}
home/karenpetzb/library/Zend/Json/Server.php000060400000035600150715512300015074 0ustar00<?php
/**
 * Zend Framework
 *
 * LICENSE
 *
 * This source file is subject to the new BSD license that is bundled
 * with this package in the file LICENSE.txt.
 * It is also available through the world-wide-web at this URL:
 * http://framework.zend.com/license/new-bsd
 * If you did not receive a copy of the license and are unable to
 * obtain it through the world-wide-web, please send an email
 * to license@zend.com so we can send you a copy immediately.
 *
 * @category   Zend
 * @package    Zend_Json
 * @copyright  Copyright (c) 2005-2008 Zend Technologies USA Inc. (http://www.zend.com)
 * @license    http://framework.zend.com/license/new-bsd     New BSD License
 */

/**
 * @see Zend_Server_Abstract
 */
require_once 'Zend/Server/Abstract.php';

/**
 * @category   Zend
 * @package    Zend_Json
 * @copyright  Copyright (c) 2005-2008 Zend Technologies USA Inc. (http://www.zend.com)
 * @license    http://framework.zend.com/license/new-bsd     New BSD License
 */
class Zend_Json_Server extends Zend_Server_Abstract
{
    /**#@+
     * Version Constants
     * @const string
     */
    const VERSION_1 = '1.0';
    const VERSION_2 = '2.0';
    /**#@-*/

    /**
     * Flag: whether or not to auto-emit the response
     * @var bool
     */
    protected $_autoEmitResponse = true;

    /**
     * @var bool Flag; allow overwriting existing methods when creating server definition
     */
    protected $_overwriteExistingMethods = true;

    /**
     * Request object
     * @var Zend_Json_Server_Request
     */
    protected $_request;

    /**
     * Response object
     * @var Zend_Json_Server_Response
     */
    protected $_response;

    /**
     * SMD object
     * @var Zend_Json_Server_Smd
     */
    protected $_serviceMap;

    /**
     * SMD class accessors
     * @var array
     */
    protected $_smdMethods;

    /**
     * @var Zend_Server_Description
     */
    protected $_table;

    /**
     * Attach a function or callback to the server
     * 
     * @param  string|array $function Valid PHP callback
     * @param  string $namespace  Ignored
     * @return Zend_Json_Server
     */
    public function addFunction($function, $namespace = '')
    {
        if (!is_string($function) && (!is_array($function) || (2 > count($function)))) {
            require_once 'Zend/Json/Server/Exception.php';
            throw new Zend_Json_Server_Exception('Unable to attach function; invalid');
        }

        if (!is_callable($function)) {
            require_once 'Zend/Json/Server/Exception.php';
            throw new Zend_Json_Server_Exception('Unable to attach function; does not exist');
        }

        $argv = null;
        if (2 < func_num_args()) {
            $argv = func_get_args();
            $argv = array_slice($argv, 2);
        }

        require_once 'Zend/Server/Reflection.php';
        if (is_string($function)) {
            $method = Zend_Server_Reflection::reflectFunction($function, $argv, $namespace);
        } else {
            $class  = array_shift($function);
            $action = array_shift($function);
            $reflection = Zend_Server_Reflection::reflectClass($class, $argv, $namespace);
            $methods = $reflection->getMethods();
            $found   = false;
            foreach ($methods as $method) {
                if ($action == $method->getName()) {
                    $found = true;
                    break;
                }
            }
            if (!$found) {
                $this->fault('Method not found', -32601);
                return $this;
            }
        }

        $definition = $this->_buildSignature($method);
        $this->_addMethodServiceMap($definition);

        return $this;
    }

    /**
     * Register a class with the server
     * 
     * @param  string $class 
     * @param  string $namespace Ignored
     * @param  mixed $argv Ignored
     * @return Zend_Json_Server
     */
    public function setClass($class, $namespace = '', $argv = null)
    {
        $argv = null;
        if (3 < func_num_args()) {
            $argv = func_get_args();
            $argv = array_slice($argv, 3);
        }

        require_once 'Zend/Server/Reflection.php';
        $reflection = Zend_Server_Reflection::reflectClass($class, $argv, $namespace);

        foreach ($reflection->getMethods() as $method) {
            $definition = $this->_buildSignature($method, $class);
            $this->_addMethodServiceMap($definition);
        }
        return $this;
    }

    /**
     * Indicate fault response
     * 
     * @param  string $fault 
     * @param  int $code 
     * @return false
     */
    public function fault($fault = null, $code = 404, $data = null)
    {
        require_once 'Zend/Json/Server/Error.php';
        $error = new Zend_Json_Server_Error($fault, $code, $data);
        $this->getResponse()->setError($error);
        return $error;
    }

    /**
     * Handle request
     * 
     * @param  Zend_Json_Server_Request $request 
     * @return null|Zend_Json_Server_Response
     */
    public function handle($request = false)
    {
        if ((false !== $request) && (!$request instanceof Zend_Json_Server_Request)) {
            require_once 'Zend/Json/Server/Exception.php';
            throw new Zend_Json_Server_Exception('Invalid request type provided; cannot handle');
        } elseif ($request) {
            $this->setRequest($request);
        }

        // Handle request
        $this->_handle();

        // Get response
        $response = $this->_getReadyResponse();

        // Emit response?
        if ($this->autoEmitResponse()) {
            echo $response;
            return;
        }

        // or return it?
        return $response;
    }

    /**
     * Load function definitions
     * 
     * @param  array|Zend_Server_Definition $definition 
     * @return void
     */
    public function loadFunctions($definition)
    {
        if (!is_array($definition) && (!$definition instanceof Zend_Server_Definition)) {
            require_once 'Zend/Json/Server/Exception.php';
            throw new Zend_Json_Server_Exception('Invalid definition provided to loadFunctions()');
        }

        foreach ($definition as $key => $method) {
            $this->_table->addMethod($method, $key);
            $this->_addMethodServiceMap($method);
        }
    }

    public function setPersistence($mode)
    {
    }

    /**
     * Set request object
     * 
     * @param  Zend_Json_Server_Request $request 
     * @return Zend_Json_Server
     */
    public function setRequest(Zend_Json_Server_Request $request)
    {
        $this->_request = $request;
        return $this;
    }

    /**
     * Get JSON-RPC request object
     * 
     * @return Zend_Json_Server_Request
     */
    public function getRequest()
    {
        if (null === ($request = $this->_request)) {
            require_once 'Zend/Json/Server/Request/Http.php';
            $this->setRequest(new Zend_Json_Server_Request_Http());
        }
        return $this->_request;
    }

    /**
     * Set response object
     * 
     * @param  Zend_Json_Server_Response $response 
     * @return Zend_Json_Server
     */
    public function setResponse(Zend_Json_Server_Response $response)
    {
        $this->_response = $response;
        return $this;
    }

    /**
     * Get response object
     * 
     * @return Zend_Json_Server_Response
     */
    public function getResponse()
    {
        if (null === ($response = $this->_response)) {
            require_once 'Zend/Json/Server/Response/Http.php';
            $this->setResponse(new Zend_Json_Server_Response_Http());
        }
        return $this->_response;
    }

    /**
     * Set flag indicating whether or not to auto-emit response
     * 
     * @param  bool $flag 
     * @return Zend_Json_Server
     */
    public function setAutoEmitResponse($flag)
    {
        $this->_autoEmitResponse = (bool) $flag;
        return $this;
    }

    /**
     * Will we auto-emit the response?
     * 
     * @return bool
     */
    public function autoEmitResponse()
    {
        return $this->_autoEmitResponse;
    }

    // overloading for SMD metadata
    /**
     * Overload to accessors of SMD object
     * 
     * @param  string $method 
     * @param  array $args 
     * @return mixed
     */
    public function __call($method, $args)
    {
        if (preg_match('/^(set|get)/', $method, $matches)) {
            if (in_array($method, $this->_getSmdMethods())) {
                if ('set' == $matches[1]) {
                    $value = array_shift($args);
                    $this->getServiceMap()->$method($value);
                    return $this;
                } else {
                    return $this->getServiceMap()->$method();
                }
            }
        }
        return null;
    }

    /**
     * Retrieve SMD object
     * 
     * @return Zend_Json_Server_Smd
     */
    public function getServiceMap()
    {
        if (null === $this->_serviceMap) {
            require_once 'Zend/Json/Server/Smd.php';
            $this->_serviceMap = new Zend_Json_Server_Smd();
        }
        return $this->_serviceMap;
    }

    /**
     * Add service method to service map
     * 
     * @param  Zend_Server_Reflection_Function $method 
     * @return void
     */
    protected function _addMethodServiceMap(Zend_Server_Method_Definition $method)
    {
        $serviceInfo = array(
            'name'   => $method->getName(),
            'return' => $this->_getReturnType($method),
        );
        $params = $this->_getParams($method);
        $serviceInfo['params'] = $params;
        $serviceMap = $this->getServiceMap();
        if (false !== $serviceMap->getService($serviceInfo['name'])) {
            $serviceMap->removeService($serviceInfo['name']);
        }
        $serviceMap->addService($serviceInfo);
    }

    /**
     * Translate PHP type to JSON type
     * 
     * @param  string $type 
     * @return string
     */
    protected function _fixType($type)
    {
        return $type;
    }

    /**
     * Get default params from signature
     * 
     * @param  array $args 
     * @param  array $params 
     * @return array
     */
    protected function _getDefaultParams(array $args, array $params)
    {
        $defaultParams = array_slice($params, count($args));
        foreach ($defaultParams as $param) {
            $value = null;
            if (array_key_exists('default', $param)) {
                $value = $param['default'];
            }
            array_push($args, $value);
        }
        return $args;
    }

    /**
     * Get method param type
     * 
     * @param  Zend_Server_Reflection_Function_Abstract $method 
     * @return string|array
     */
    protected function _getParams(Zend_Server_Method_Definition $method)
    {
        $params = array();
        foreach ($method->getPrototypes() as $prototype) {
            foreach ($prototype->getParameterObjects() as $key => $parameter) {
                if (!isset($params[$key])) {
                    $params[$key] = array(
                        'type'     => $parameter->getType(),
                        'name'     => $parameter->getName(),
                        'optional' => $parameter->isOptional(),
                    );
                    if (null !== ($default = $parameter->getDefaultValue())) {
                        $params[$key]['default'] = $default;
                    }
                    $description = $parameter->getDescription();
                    if (!empty($description)) {
                        $params[$key]['description'] = $description;
                    }
                    continue;
                }
                $newType = $parameter->getType();
                if (!is_array($params[$key]['type'])) {
                    if ($params[$key]['type'] == $newType) {
                        continue;
                    }
                    $params[$key]['type'] = (array) $params[$key]['type'];
                } elseif (in_array($newType, $params[$key]['type'])) {
                    continue;
                }
                array_push($params[$key]['type'], $parameter->getType());
            }
        }
        return $params;
    }

    /**
     * Set response state
     * 
     * @return Zend_Json_Server_Response
     */
    protected function _getReadyResponse()
    {
        $request  = $this->getRequest();
        $response = $this->getResponse();

        $response->setServiceMap($this->getServiceMap());
        if (null !== ($id = $request->getId())) {
            $response->setId($id);
        }
        if (null !== ($version = $request->getVersion())) {
            $response->setVersion($version);
        }

        return $response;
    }

    /**
     * Get method return type
     * 
     * @param  Zend_Server_Reflection_Function_Abstract $method 
     * @return string|array
     */
    protected function _getReturnType(Zend_Server_Method_Definition $method)
    {
        $return = array();
        foreach ($method->getPrototypes() as $prototype) {
            $return[] = $prototype->getReturnType();
        }
        if (1 == count($return)) {
            return $return[0];
        }
        return $return;
    }

    /**
     * Retrieve list of allowed SMD methods for proxying
     * 
     * @return array
     */
    protected function _getSmdMethods()
    {
        if (null === $this->_smdMethods) {
            $this->_smdMethods = array();
            require_once 'Zend/Json/Server/Smd.php';
            $methods = get_class_methods('Zend_Json_Server_Smd');
            foreach ($methods as $key => $method) {
                if (!preg_match('/^(set|get)/', $method)) {
                    continue;
                }
                if (strstr($method, 'Service')) {
                    continue;
                }
                $this->_smdMethods[] = $method;
            }
        }
        return $this->_smdMethods;
    }

    /**
     * Internal method for handling request
     * 
     * @return void
     */
    protected function _handle()
    {
        $request = $this->getRequest();

        if (!$request->isMethodError() && (null === $request->getMethod())) {
            return $this->fault('Invalid Request', -32600);
        }

        if ($request->isMethodError()) {
            return $this->fault('Invalid Request', -32600);
        }

        $method = $request->getMethod();
        if (!$this->_table->hasMethod($method)) {
            return $this->fault('Method not found', -32601);
        }

        $params        = $request->getParams();
        $invocable     = $this->_table->getMethod($method);
        $serviceMap    = $this->getServiceMap();
        $service       = $serviceMap->getService($method);
        $serviceParams = $service->getParams();

        if (count($params) < count($serviceParams)) {
            $params = $this->_getDefaultParams($params, $serviceParams);
        }

        try {
            $result = $this->_dispatch($invocable, $params);
        } catch (Exception $e) {
            return $this->fault($e->getMessage(), $e->getCode());
        }

        $this->getResponse()->setResult($result);
    }
}