Note:

If you want to create a new page for developers, you should create it on the Moodle Developer Resource site.

Webservice protocols: Difference between revisions

From MoodleDocs
m (Text replacement - "<code php>" to "<syntaxhighlight lang="php">")
 
(22 intermediate revisions by 3 users not shown)
Line 1: Line 1:
<p class="note">'''Note:''' This page is  a work-in-progress. ''Comments and suggestions are welcome!'' Please use the [[{{TALKPAGENAME}}|page comments]].</p>
=Introduction=
=Introduction=
Web service protocol plugins are web service servers. These servers let external applications call Moodle web service functions in an specific protocol: REST / AMF / SOAP /XML-RPC / ...
Web service protocol plugins are web service servers. These servers let external applications call Moodle web service functions in an specific protocol: REST / AMF / SOAP /XML-RPC / ...
Line 7: Line 5:
The easiest example is the [https://github.com/moodle/moodle/tree/master/webservice/rest REST server].
The easiest example is the [https://github.com/moodle/moodle/tree/master/webservice/rest REST server].


=Naming conventions=
describe naming conventions
=File structure=
=File structure=
describe the basic structure of the files and what they are for
==webservice/myprotocol/db/access.php==
clarify required vs optional
Since  Moodle 3.0 protocols capabilities don't have risks attached. See MDL-50613 for more information.
=Interfacing to APIs=
<syntaxhighlight lang="php">
list all the callbacks that must be defined, link to relevant API docs
<?php
list all other optional callbacks as well, linking to relevant API docs
 
=Database tables=
/**
describe all the tables that must be implemented
* myprotocol server related capabilities
describe how to store addtional data
*
=TODO=
* @package    webservice_myprotocol
* @category  access
* @copyright  20XX Your Name
* @license    http://www.gnu.org/copyleft/gpl.html GNU GPL v3 or later
*/
 
$capabilities = array(
 
    'webservice/myprotocol:use' => array(
        'captype' => 'read', // in fact this may be considered read and write at the same time
        'contextlevel' => CONTEXT_COURSE, // the context level should be probably CONTEXT_MODULE
        'archetypes' => array(
        ),
    ),
 
);
</syntaxhighlight>
 
==webservice/myprotocol/lang/en/webservice_myprotocol.php==
<syntaxhighlight lang="php">
<?php
 
/**
* Strings for component 'webservice_myprotocol', language 'en', branch 'MOODLE_XX_STABLE'
*
* @package    webservice_myprotocol
* @category  string
* @copyright  20XX Your Name
* @license    http://www.gnu.org/copyleft/gpl.html GNU GPL v3 or later
*/
 
$string['pluginname'] = 'myprotocol protocol';
$string['myprotocol:use'] = 'Use myprotocol protocol';
</syntaxhighlight>
 
==webservice/myprotocol/server.php==
This is the entry point of your server. The web service clients will call this file with the web service function name/parameters and the web service token. In this file you could want to catch some other $_REQUEST parameters as the [https://github.com/moodle/moodle/blob/master/webservice/rest/server.php#L37-47 REST server] does. But it's most likely that very few changes are going to be done here.
<syntaxhighlight lang="php">
<?php
/**
* myprotocol web service entry point. The authentication is done via tokens.
*
* @package    webservice_myprotocol
* @copyright  20XX Your Name
* @license    http://www.gnu.org/copyleft/gpl.html GNU GPL v3 or later
*/
 
/**
* NO_DEBUG_DISPLAY - disable moodle specific debug messages and any errors in output
*/
define('NO_DEBUG_DISPLAY', true);
 
/**
* NO_MOODLE_COOKIES - no cookies with web service
*/
define('NO_MOODLE_COOKIES', true);
 
require('../../config.php');
require_once("$CFG->dirroot/webservice/myprotocol/locallib.php");
 
if (!webservice_protocol_is_enabled('myprotocol')) {
    die;
}
 
$server = new webservice_rest_server(WEBSERVICE_AUTHMETHOD_PERMANENT_TOKEN);
$server->run();
die;
</syntaxhighlight>
 
==webservice/myprotocol/locallib.php==
That's where all the magic happens. Have a look how the [https://github.com/moodle/moodle/blob/master/webservice/rest/locallib.php REST server] or the [https://github.com/moodle/moodle/blob/master/webservice/lib.php#L870-1290 Zend servers] extend ''webservice_base_server''.
 
<syntaxhighlight lang="php">
<?php
 
/**
* myprotocol web service implementation classes and methods.
*
* @package    webservice_myprotocol
* @copyright  20XX Your Name
* @license    http://www.gnu.org/copyleft/gpl.html GNU GPL v3 or later
*/
 
require_once("$CFG->dirroot/webservice/lib.php");
 
/**
* myprotocol service server implementation.
*
* @package    webservice_myprotocol
* @copyright  20XX Your Name
* @license    http://www.gnu.org/copyleft/gpl.html GNU GPL v3 or later
*/
class webservice_myprotocol_server extends webservice_base_server {
 
    /**
    * Contructor
    *
    * @param string $authmethod authentication method of the web service (WEBSERVICE_AUTHMETHOD_PERMANENT_TOKEN, ...)
    */
    public function __construct($authmethod) {
        parent::__construct($authmethod);
    }
 
    /**
    * This method parses the $_REQUEST
    */
    protected function parse_request() {
      //Retrieve the user credentials (token / ...), the web service function parameters, ...
      $this->token = isset($_REQUEST['wstoken']) ? $_REQUEST['wstoken'] : null;
      unset($_REQUEST['wstoken']);
 
      $this->functionname = isset($_REQUEST['wsfunction']) ? $_REQUEST['wsfunction'] : null;
      unset($_REQUEST['wsfunction']);
 
      $this->parameters = $_REQUEST;
    }
 
    /**
    * Send the result of function call to the WS client
    */
    protected function send_response() {
 
        // Check that the returned values are valid
        // sometimes it is not necessary like for Zend servers where
        // the cleaning is done in service_class_method_body() of the webservice_zend_server class
        try {
            $validatedvalues = external_api::clean_returnvalue($this->function->returns_desc, $this->returns);
        } catch (Exception $ex) {
            $exception = $ex;
        }
 
        //PROCESS THE RESPONSE
        echo $response;
    }
 
    /**
    * Send the error information to the WS client
    * @param exception $ex the exception that we are sending
    */
    protected function send_error($ex=null) {
        //PROCESS THE ERROR MESSAGE
        echo $error;
    }
 
}
 
</syntaxhighlight>
 
==webservice/myprotocol/version.php==
<syntaxhighlight lang="php">
<?php
 
/**
* Version details
*
* @package    webservice_myprotocol
* @copyright  20XX Your Name
* @license    http://www.gnu.org/copyleft/gpl.html GNU GPL v3 or later
*/
 
defined('MOODLE_INTERNAL') || die();
 
$plugin->version  = YYYYMMDDXX;        // The current plugin version (Date: YYYYMMDDXX)
$plugin->requires  = yyyymmddxx;        // Requires this Moodle version
$plugin->component = 'webservice_myprotocol'; // Full name of the plugin (used for diagnostics)
 
</syntaxhighlight>


*Link your pages to type in Frankenstyle page
[[Category:Web Services]]
*Link your pages to type in Plugins page
[[Category:Plugins]]
*Add pages to Plugins category
*This should be done for following plugin's: https://docs.moodle.org/dev/Frankenstyle#Plugin_types

Latest revision as of 20:34, 14 July 2021

Introduction

Web service protocol plugins are web service servers. These servers let external applications call Moodle web service functions in an specific protocol: REST / AMF / SOAP /XML-RPC / ...

Examples

The easiest example is the REST server.

File structure

webservice/myprotocol/db/access.php

Since Moodle 3.0 protocols capabilities don't have risks attached. See MDL-50613 for more information.

<?php

/**
 * myprotocol server related capabilities
 *
 * @package    webservice_myprotocol
 * @category   access
 * @copyright  20XX Your Name
 * @license    http://www.gnu.org/copyleft/gpl.html GNU GPL v3 or later
 */

$capabilities = array(

    'webservice/myprotocol:use' => array(
        'captype' => 'read', // in fact this may be considered read and write at the same time
        'contextlevel' => CONTEXT_COURSE, // the context level should be probably CONTEXT_MODULE
        'archetypes' => array(
        ),
    ),

);

webservice/myprotocol/lang/en/webservice_myprotocol.php

<?php

/**
 * Strings for component 'webservice_myprotocol', language 'en', branch 'MOODLE_XX_STABLE'
 *
 * @package    webservice_myprotocol
 * @category   string
 * @copyright  20XX Your Name
 * @license    http://www.gnu.org/copyleft/gpl.html GNU GPL v3 or later
 */

$string['pluginname'] = 'myprotocol protocol';
$string['myprotocol:use'] = 'Use myprotocol protocol';

webservice/myprotocol/server.php

This is the entry point of your server. The web service clients will call this file with the web service function name/parameters and the web service token. In this file you could want to catch some other $_REQUEST parameters as the REST server does. But it's most likely that very few changes are going to be done here.

<?php
/**
 * myprotocol web service entry point. The authentication is done via tokens.
 *
 * @package    webservice_myprotocol
 * @copyright  20XX Your Name
 * @license    http://www.gnu.org/copyleft/gpl.html GNU GPL v3 or later
 */

/**
 * NO_DEBUG_DISPLAY - disable moodle specific debug messages and any errors in output
 */
define('NO_DEBUG_DISPLAY', true);

/**
 * NO_MOODLE_COOKIES - no cookies with web service
 */
define('NO_MOODLE_COOKIES', true);

require('../../config.php');
require_once("$CFG->dirroot/webservice/myprotocol/locallib.php");

if (!webservice_protocol_is_enabled('myprotocol')) {
    die;
}

$server = new webservice_rest_server(WEBSERVICE_AUTHMETHOD_PERMANENT_TOKEN);
$server->run();
die;

webservice/myprotocol/locallib.php

That's where all the magic happens. Have a look how the REST server or the Zend servers extend webservice_base_server.

<?php

/**
 * myprotocol web service implementation classes and methods.
 *
 * @package    webservice_myprotocol
 * @copyright  20XX Your Name
 * @license    http://www.gnu.org/copyleft/gpl.html GNU GPL v3 or later
 */

require_once("$CFG->dirroot/webservice/lib.php");

/**
 * myprotocol service server implementation.
 *
 * @package    webservice_myprotocol
 * @copyright  20XX Your Name
 * @license    http://www.gnu.org/copyleft/gpl.html GNU GPL v3 or later
 */
class webservice_myprotocol_server extends webservice_base_server {

    /**
     * Contructor
     *
     * @param string $authmethod authentication method of the web service (WEBSERVICE_AUTHMETHOD_PERMANENT_TOKEN, ...)
     */
    public function __construct($authmethod) {
        parent::__construct($authmethod);
    }

    /**
     * This method parses the $_REQUEST
     */
    protected function parse_request() {
       //Retrieve the user credentials (token / ...), the web service function parameters, ...
       $this->token = isset($_REQUEST['wstoken']) ? $_REQUEST['wstoken'] : null;
       unset($_REQUEST['wstoken']);

       $this->functionname = isset($_REQUEST['wsfunction']) ? $_REQUEST['wsfunction'] : null;
       unset($_REQUEST['wsfunction']);

       $this->parameters = $_REQUEST;
    }

    /**
     * Send the result of function call to the WS client
     */
    protected function send_response() {

        // Check that the returned values are valid
        // sometimes it is not necessary like for Zend servers where 
        // the cleaning is done in service_class_method_body() of the webservice_zend_server class
        try {
            $validatedvalues = external_api::clean_returnvalue($this->function->returns_desc, $this->returns);
        } catch (Exception $ex) {
            $exception = $ex;
        }

        //PROCESS THE RESPONSE
        echo $response;
    }

    /**
     * Send the error information to the WS client
     * @param exception $ex the exception that we are sending
     */
    protected function send_error($ex=null) {
        //PROCESS THE ERROR MESSAGE
        echo $error;
    }

}

webservice/myprotocol/version.php

<?php

/**
 * Version details
 *
 * @package    webservice_myprotocol
 * @copyright  20XX Your Name
 * @license    http://www.gnu.org/copyleft/gpl.html GNU GPL v3 or later
 */

defined('MOODLE_INTERNAL') || die();

$plugin->version   = YYYYMMDDXX;        // The current plugin version (Date: YYYYMMDDXX)
$plugin->requires  = yyyymmddxx;        // Requires this Moodle version
$plugin->component = 'webservice_myprotocol'; // Full name of the plugin (used for diagnostics)