Docs »


Add new functionality to Cerb

While Cerb’s source code is 100% public, any customizations you make to the platform itself will likely “conflict” with ongoing improvements made by the official developers. This makes it more difficult for you to upgrade.

You can avoid these issues by using plugins – optional bundles of files that seamlessly contribute new functionality to Cerb.

Even the built-in functionality in Cerb is contributed by plugins. This way, as we continue to improve Cerb, we’re also automatically expanding the ability for other people to build their own customizations too.

Common uses for plugins are:

Plugins also allow unused functionality to be removed to keep everything simpler and more efficient.


Every plugin must have a unique ID comprised of lowercase letters (a-z), numbers (0-9), underscores (_), and dots (.).

By convention, the first segment of a plugin’s ID is a namespace unique to its author. One way to ensure uniqueness is to base your namespace on a domain name you own.

For instance: com.example.plugin_name


Every plugin is a directory with the same name as its ID, using the following filesystem structure:

Path Description
api/ Extensions
patches/ Patches
resources/ Resources (images, scripts, stylesheets)
templates/ Templates
plugin.xml Manifest
strings.xml Translations

The minimal set of plugins required for Cerb to work properly are called features. You’ll find them in the features/ directory.

Third-party plugins are found in the storage/plugins/ directory. These plugins are installed and automatically updated from the Plugin Library.


Each plugin must have a manifest file named plugin.xml that describes its contents. This tells Cerb what kinds of new functionality the plugin is contributing.

Here’s a minimal manifest:

<?xml version="1.0" encoding="UTF-8"?>
<plugin xmlns:xsi="" xsi:noNamespaceSchemaLocation="">
	<name>Plugin Name</name>
	<description>This explains what your plugin does.</description>
	<author>Webgroup Media, LLC.</author>

		<app_version min="9.3" max="9.3.99" />
		<!--<php_extension name="curl" />-->

		<require plugin_id="cerberusweb.core" version="9.3.0" />


Plugin metadata

  • <id> is the globally unique ID of the plugin, prefixed with the author’s namespace. This should only contain lowercase letters (a-z), numbers (0-9), underscore (_), and dots (.).

  • <name> is the human-friendly name of the plugin.

  • <description> is a brief description of the purpose and contributions of the plugin.

  • <author> is the name used for attribution of the plugin’s author.

  • <version> is the semantic version of the plugin in <generation>.<major>.<minor> format. This should start with 0.0.0 and be incremented for each update.

  • <link> is a URL to the plugin’s documentation page.

  • <image> is a path to the plugin’s icon. This is relative to the plugin’s resources/ directory.


The <requires> block specifies the requirements for installing and enabling this plugin.

This block must contain one <app_version> element specifying the minimum and maximum version of Cerb that are verified compatible with this build of the plugin.

The block may contain any number of <php_extension> elements if specific PHP extensions are required for the plugin to operate (e.g. ldap, oauth, zip).


The optional <dependencies> block specifies if this plugin depends on another plugin.

This block may contain any number of <require> elements specifying a required plugin_id and its minimum compatible version.

Everything else

The other elements will be covered in more detail in the subsequent sections:


Plugins contribute new functionality by registering extensions on extension points.

Extensions are defined in a plugin’s manifest within the <extensions> block.

Each extension entry looks like:

<extension point="com.example.extension_point">
	<name>Extension name</name>

  • <extension point="..."> specifies the extension point of the extension.

  • <id> is the globally unique ID of the extension. Like plugins, this should only contain lowercase letters (a-z), numbers (0-9), underscores (_), and dots (.). The extension ID should always start with the ID of the plugin.

  • <name> is the human-friendly name of the extension.

  • <class> assigns code from the plugin to the extension. Each extension point provides a parent class which must be extended by the plugin’s extension. The <name> element in this block specifies the class name of this implementation, and <file> is the path to a source code file, relative to the plugin’s directory. This almost always starts with api/.

  • <params> is where each extension manifest can set configuration details based on the extension point.

Extension points

Name Extension Point
Automation Trigger devblocks.event.action
Bot Action devblocks.event.action
Bot Event devblocks.event
Cache Engine devblocks.cache.engine
Calendar Datasource cerberusweb.calendar.datasource
Card Widget Type cerb.card.widget
Community Portal cerb.portal
Connected Service Provider cerb.connected_service.provider
Controller devblocks.controller
Custom Field Type cerb.custom_field
Event Listener devblocks.listener.event
Http Request Listener devblocks.listener.http
Mail Transport Type cerberusweb.mail.transport
Page Menu Item
Page Section
Page Type
Prebody Renderer cerberusweb.renderer.prebody
Profile Tab Type
Profile Widget Type
Record Type devblocks.context
Resource Type cerb.resource.type
Rest API Controller
Scheduled Job cerberusweb.cron
Search Engine
Search Schema
Sensor Type cerberusweb.datacenter.sensor
Storage Engine
Storage Schema
Support Center Controller
Support Center Login Authenticator usermeet.login.authenticator
Support Center RSS Feed
Workspace Page Type
Workspace Tab Type
Workspace Widget Datasource cerberusweb.ui.workspace.widget.datasource
Workspace Widget Type cerberusweb.ui.workspace.widget


Plugins can add new events to Cerb based on the contributed functionality. The activity log will record the new events on records, automations can listen for them, etc.

	<event id="example.event">
		<name>Example Event</name>
		<param key="field_name" />

  • <event id="..."> specifies the ID of the event.

  • <name> is the human-friendly name of the event.

  • <param key="..."> is a list of available parameters on the event.

If you create a Bot Event extension you do not need to add a separate event here.


Plugins that need to maintain a schema in the database can do so with patches. A patch is a collection of changes used to migrate data between versions during an upgrade.

When you skip several versions of a plugin to upgrade to the latest version, Cerb will automatically handle the migration of your data through the intervening versions. This is the same thing that happens when you upgrade Cerb itself.

	<patch version="9.0.0" revision="1" file="patches/9.0.0.php" />


The class loader is a map of source code classes and their filesystem paths. This enables Cerb to efficiently only load the files necessary to serve a specific request.

If your plugin introduces classes that will be referenced by code outside of the plugin, you should register them here. Class loader entries are automatically created for any extensions you register.

	<file path="api/dao/example.php">
		<class name="Context_Example" />
		<class name="DAO_Example" />
		<class name="Model_Example" />
		<class name="Plugin_Example" />
		<class name="SearchFields_Example" />
		<class name="View_Example" />


Plugins can introduce new privileges into roles.

	<priv id="example.permission" label="acl.example.permission" />

  • id="..." is the ID of the new privilege. This uses dot-notation like plugins and extensions. It should also use your plugin ID as a namespace prefix.

  • label="..." is the translation ID of the human-readable label for the privilege.


Most of the text you see in Cerb is provided by the translation system using American English defaults. All of this text is able to be translated into any other language using our built-in Translation Editor plugin.

Plugins can add new text to the translation system with a strings.xml file in TMX format, which can then be translated into any language by anyone, as well as shared in our official translation packs.

<?xml version="1.0" encoding="UTF-8"?>
<!DOCTYPE tmx PUBLIC "-//LISA OSCAR:1998//DTD for Translation Memory eXchange//EN" "tmx14.dtd">
<tmx version="1.4">
	<header creationtool="Cerb" creationtoolversion="9.0.7" srclang="en_US" adminlang="en" datatype="unknown" o-tmf="unknown" segtype="sentence" creationid="" creationdate=""/>

		<tu tuid='example.plugin.string_name'>
			<tuv xml:lang="en_US"><seg>Replace this with your own text.</seg></tuv>


Plugins can add new sharable resources like:

  • Images

  • Scripts (Javascript)

  • Stylesheets

These must be stored in the resources/ directory within the plugin.

Resources can then be accessed by URL with the format:


In templates:


From bot scripting:


All plugin resources are public (world readable) and do not require a valid session to access. Do not store private content in this directory.


Cerb plugins use the Smarty template engine.

Templates are stored in the plugin’s templates/ directory.

They are referenced from plugin code like:

$tpl = DevblocksPlatform::services()->template();
$tpl->assign('name', 'Kina Halpue');

In ->display(), example.plugin should be your plugin’s ID. The path/to/ is relative to the plugin’s templates/ directory.

Here’s an example template:

	Hello, <b>{$name}</b>!

Activity Points

We previously mentioned events when discussing automations and the activity log. Plugins can add new events to Cerb based on the contributed functionality. The activity log will record the new events on records, automations can listen for them, etc.

	<activity point="example.event">
		<param key="label_key" value="Example Event" />
		<param key="string_key" value="activities.example_event" />
		<param key="options" value="api_create, notifications" />



Devblocks devblocks.core
Cerb Core cerberusweb.core
Chat Bots cerb.bots.portal.widget
Knowledgebase cerberusweb.kb
Project Boards cerb.project_boards
Support Center cerberusweb.support_center
Web Services API (JSON/XML) cerberusweb.restapi
Webhooks cerb.webhooks


LDAP Integration wgm.ldap


JIRA Integration wgm.jira


Legacy Printing cerb.legacy.print
Legacy Profile Attachments Download cerb.legacy.profile.attachments
Ticket Profile “Move To” Shortcut cerb.profile.ticket.moveto
Notifications Emailer wgm.notifications.emailer
Record Simulator cerberusweb.simulator


Translation Editor cerberusweb.translators

Record Types

Call Logging cerberusweb.calls
Collaborative Feed Reader cerberusweb.feed_reader
Feedback Capture
Opportunity Tracking cerberusweb.crm
Sensors cerberusweb.datacenter.sensors
Servers cerberusweb.datacenter.servers
Time Tracking cerberusweb.timetracking


S3 Gatekeeper Storage Engine