[cvs] [Wiki] created: CustomizeApis

Jan Schneider jan at horde.org
Thu Feb 21 11:28:48 UTC 2008


jan  Thu, 21 Feb 2008 06:28:48 -0500

Created page: http://wiki.horde.org/CustomizeApis

+ Replacing APIs with own solutions

Horde applications are loosely coupled with each other through the
application APIs. Each application provides a set of external API methods
that can be called from other Horde applications through the Horde Registry,
or even externally through the Horde RPC interfaces. See the
((Doc/Dev/Registry|Registry wiki page)) for details.

If you want to provide some functionality through your own or some external
code, all you need to do it to register you own code in the Horde Registry
and provide the required API methods. If you have your own address book or
CRM solution, you could replace Horde address book module Turba with that
program for example.

Here is some real world example. Say we have some CRM system that is
providing contacts. First create a small application stub, a Horde
mini-application. We call it "crm" and need the following 3 files to become
a working Horde module:

<code>
horde/config/registry.d/crm.php
horde/crm/config/conf.php
horde/crm/lib/api.php
</code>

The {{registry.d/}} directory exists since Horde 3.2. For earlier versions,
add the code from {{crm.php}} directly to {{horde/config/registry.php}}. The
directory in newer versions is more flexible since you can update the
{{registry.php}} configuration file more easily when upgrading to newer
Horde versions if you didn't customize it.

The {{conf.php}} can be empty. The {{crm.php}} file looks like:

<code type="php">
<?php
$this->applications['crm'] = array(
    'fileroot' => dirname(__FILE__) . '/../../crm',
    'webroot' => $this->applications['horde']['webroot'] . '/crm',
    'name' => 'CRM',
    'status' => 'notoolbar',
    'provides' => array('contacts'),
);
</code>

This entry registers an application called "crm" at the Horde Registry,
hides it from the toolbar (we only want to use it internally, i.e. it
doesn't have a UI), and propagates the "contacts" API. This means that all
methods calls to the contacts API will be delegated to the crm module. Turba
provides a **lot** of methods through the contacts API, just take a look at
{{turba/lib/api.php}} to get an impression. You don't have to implement all
these methods in your crm module though, because a) not all methods are used
in all Horde modules (see below), and b) you can also tell the registry to
only provide certain methods of the contacts API. To achieve that, change
the {{'provides'}} entry to a less generic value:

<code type="php">
'provides' => array('contacts/search', 'contacts/show'),
</code>

This tells the Registry that your are only providing the "search" and "show"
methods of the "contacts" API. The other methods may be provided by other
modules, by Turba, or not at all. {{'provides'}} entries with method names
take precedence over generic entries, i.e. if for Turba you have
{{'provides' => array('contacts')}} in the registry configuration and
{{'provides' => array('contacts/search', 'contacts/show')}} for your own
module, than these two method will be routed to your module, all other
"contacts/" calls will be delegated to Turba.

The {{api.php}} file finally provides the actual method definitions. At the
top of the file, you list all methods that your are going to provide in this
file, including the method signatures:

<code type="php">
<?php
/**
 * CRM external API interface.
 *
 * This file defines CRM's external Horde API interface. Other Horde
 * applications will interact with CRM through this API.
 */

$_services['search'] = array(
    'args' => array('names' => '{urn:horde}stringArray',
                    'sources' => '{urn:horde}stringArray',
                    'fields' => '{urn:horde}stringArray',
                    'matchBegin' => 'boolean'),
    'type' => '{urn:horde}stringArray',
);

$_services['show'] = array(
    'link' =>
'%application%/contact.php?source=|source|&key=|key|&uid=|uid|',
);
?>

The method signatures are only important for informational purposes and for
providing WSDL services through Horde's SOAP interface. The "show" method is
a special case because it is not really a method, but provides a link
prototype, i.e. it will be used to provide URL links to certain pages inside
the application. ##red|This has to be explained further.##

Next comes a function definition for each method propagated in the API. The
naming convention for these functions is {{_modulename_methodname}}:

<code type="php">
/**
 * Returns a contact search result.
 *
 * @param array $names          The search filter values
 * @param array $sources        The sources to serach in
 * @param array $fields         The fields to serach on
 * @param boolean $matchBegin	Match word boundries only
 *
 * @return array  Hash containing the search results.
 */
function _crm_search($names = array(), $sources = array(), $fields =
array(),
                     $matchBegin = false)
{
    // Do some nice things like searching your own application, or routing
    // to an API of a third-party application.
    ...
    return $contacts;
}
</code>

It's a good idea to start with the function definitions already provided
through existing Horde modules, to get some impression which functionality
exactly is expected, how returned or incoming data structures look like, and
how to deal with errors.

++ API methods called from the several applications

This section is going to build a list of all Horde applications and the API
methods they call. With this list you could easily see which methods you
might have to implement if want your application to work with a certain set
of Horde modules. Please remember, you don't **have to** implement all
methods. If a method doesn't exist, the functionality simply isn't available
in the Horde module that would call it.


More information about the cvs mailing list