Writing cPanel Modules
You can create your own custom Perl modules for use with cPanel plugins. Using this integration method, you can expose your application's logic as a cPanel API call. These API calls can then be used by our XML/JSON APIs, LiveAPI, or cPanel tags.
Basics
cPanel Perl modules are ordinary Perl modules that are placed in a specific directory and use the cPanel namespace.
You need to place your custom cPanel Perl modules in the following directory:
- /usr/local/cpanel/Cpanel/
Since cPanel modules are parsed internally by the cPanel software, you will not be able to call system-installed modules from your custom modules. Only a few pre-compiled modules (located in
/usr/local/cpanel/perl/) and the other modules in the
Cpanel:: namespace are available.
If you need to install additional modules, you can place them in:
Creating API 1 functions
Setting up a module that will make a custom API1 call requires a function that will operate as a constructor. This function needs to use the module's name, suffixed by
init(). This function will only need to return output, but it
is required in order for the API1 call to work successfully.
The function should resemble the following:
sub Module_init {
return;
}
In the example above,
Module represents the module name you wish to use.
Once you have set up the required function, you can use your module to print or return data. However, if you are returning more than a
string, you will need to use
API2.
A sample function within a cPanel module can be found below. This module simply prints data to the cPanel interface:
sub Module_test {
print "testing 1 2 3";
}
Adding Parameters
Passing parameters to an API1 call is exactly like passing parameters inside of any other Perl function. Data passed into the function is passed via the special
@_ variable. You can assign
$_[array index] to any given variable if you wish to pass parameters to a human-readable variable. For example:
sub Module_printLC {
my ($string1) = @_;
print lc( $string1 );
}
If, for example, you wish to pass the
<cpanel> tag, you could do so by including:
<cpanel Module="printLC(TESTING)">
The example above would print
testing to the cPanel interface.
Using Error Messages
In order to raise an error message within a cPanel module, you need to assign the error
strings to the following hash:
The key element of this hash should have the same name as the module with which you are working. For example:
sub Module_raiseError {
$Cpanel::CPERROR{'module'} = "This is an error message";
}
In the example above,
module represents the module name you wish to use.
The example above would allow you to check for the existance of an error using a
<cpanelif> tag. This can be printed and check in the interface by using
$CPERROR{'module'} inside your HTML file.
Creating API 2 functions
In order to enable your cPanel module to make custom API2 calls, you need to create a generic function titled
api2() within the module. This function specifies which API2 calls are mapped to which functions. It is also responsible for returning a hash that contains information on how the module works. There are only 2 elements of this hash that need to be returned:
- func — This element defines the function through which the call is made.
- engine — This element specifies the output format.
-
Note: engine will almost always be a hash array.
A sample
api2() function can be found below:
sub api2 {
my $func = shift;
my %API;
$API{'functionName'}{'func'} = "api2_test";
$API{'functionName'}{'engine'} = 'hasharray';
return \%{ $API{ $func } };
}
Since the API2 system uses named prameters, the
@_ variable will need to be assigned to a hash like so:
sub api2_test {
my %OPTS = @_;
}
Remember: As a convention, you should use the
%OPTS hash for API2 input parameters.
Once you have created this function within your cPanel module, any data passed to the function within a
<?cp ?> tag can be accessed as an element of that hash. As an example, assume the
<?cp ?> tag has been passed the following information:
<?cp Module::test( %, data, ) number="5" ?>
In this example, after
%OPTS has been properly assigned, you will be able to access the
number variable via
$OPTS{'number'};. For example:
sub api2_test {
my %OPTS = @_;
my $number = $OPTS{'number'};
}
Returning Data
The API2 system must return a
hash reference or an
array of hash references if you intend to use the call within
<?cp ?> tags. Elements within the returned reference must either be
arrays of hash references or
scalar variables.
Note: These restrictions do not apply to cPanel calls made through the XML API system.
Returning a Hash
One acceptable return format for API2 is a normal hash reference. It will need to be formatted like the following example:
{
key => "value"
}
In the example above,
key can be accessed via the
<?cp ?> tags when laid out like so:
<?cp Module::function( %, key, ) ?>
The example above will print
value when accessed via a web browser.
Returning an Array of Hashes
Another acceptable return format is an array reference of hash references. For example:
[
{
key => "value1"
},
{
key => "value2"
}
]
In the example above, the template will be applied to each element of the array when calling API2 functions via the
<?cp ?> tags. In this particular scenario:
<? Module::function( % [br /], key, ) ?>
The example above, when given an array of hashes, will display the following:
value 1
value 2
An Array of Hashes as a Hash Element
Values within hashes do not have to be scalar variables. These values can also be arrays of hashes.
Note: Nested hash elements and nested arrays cannot be accepted.
Using this method, your data would need to be modeled after the following example:
{
element => [
{
key => "value1"
},
{
key => "value2"
}
]
another_element => "testing"
}
In order to call this data using
<?cp ?> tags, you would need to use the following format:
<?cp Module::function(
% [br /]%,
another_element,
element:: KEY-${key}[br /]:
)
?>
The example above would output the following:
testing <br>
KEY-value1 <br>
KEY-value2 <br>