Руководство по плагинам

Плагины предоставляют вам возможность добавлять пользовательские функции к CumulusClips без изменения файлов ядра. Это важно, поскольку большинство основных файлов будут перезаписаны в процессе обновления, поэтому любые изменения, внесенные в эти файлы будут потеряны.

Обзор

В мире CumulusClips плагины являются классами PHP. Они содержат функции, которые выполняют пользовательский код разработчика. CumulusClips использует систему плагинов на основе событий. Это подразумевает что исполнение функций может быть привязано к общим системным событиям. Когда система сталкивается с перехватчиком событий, исполняются все методы плагинов, которые были закреплены за этим перехватчиком событий. Перехватчики событий рассредоточены по всему коду, во всех местах, которые наша команда сочла наиболее выгодными для разработчика. Плагины и темы могут определять свои собственные события.

Типы перехватчиков

Перехватчики бывают двух видов: событий и фильтры. Оба ведут себя почти одинаково. Иногда они принимают параметры в зависимости от контекста. В свою очередь, эти параметры передаются любому плагину, закреплённому за перехватчиком. Эти два различия заключаются в том, что методы плагинов привязанных к фильтрам должны первыми обрабатывать параметры. Это связано с тем, что отфильтрованный параметр может быть передан на вход следующему плагину или остальному базовому коду. От методов плагинов привязанных к событям не ожидается возврат значений.

События

// Внутри CumulusClips
Plugin::triggerEvent('sample.event', 'foo');

// Внутри вашего плагина
public function myPluginMethod($param)
{
    // $param содержит значение 'foo'.
    // Делаем что-то с foo
    $param;
}

Фильтры

// Внутри CumulusClips
$variable = Plugin::triggerFilter('sample.filter', 'foo');

// Внутри вашего плагина
public function myPluginMethod($param)
{
    // $param содержит начальное значение 'foo'
    // Преобразуем foo в foobar и вернём для продолжения по цепочке
    return $param . 'bar';
}

Соглашения о структуре и именах

Плагины являются только лишь классами PHP. Они наследуют класс PluginAbstract, т.е.

class MyPlugin extends PluginAbstract
{
    // Код плагина
}

Класс плагина может иметь несколько публичных свойств, общепринятых для CumulusClips. Разумеется, вы можете добавить свои, но эти также используютя как вами, так и системой:

Имя свойства Тип данных Необходимость Описание
name string True Название вашего плагина. Оно отображается в панели администратора
description string false Краткое описание или заметки для вашего плагина. Оно отображается в панели администратора
author string false Автор плагина
url string false Полный URL веб-сайта плагина
version string true Текущая версия плагина, придерживайтесь семантики версий, т.е. x.x.x

Вот пример кода плагина со встроенными свойствами:

class MyPlugin extends PluginAbstract
{
    /**
     * @var string Name of plugin
     */
    public $name = 'My Plugin';

    /**
     * @var string Description of plugin
     */
    public $description = 'Sample description';

    /**
     * @var string Name of plugin author
     */
    public $author = 'CumulusClips';

    /**
     * @var string URL to plugin's website
     */
    public $url = 'http://cumulusclips.org/';

    /**
     * @var string Current version of plugin
     */
    public $version = '1.0.0';
}

Структура плагина

Плагины хранятся в директории /cc-content/plugins. У каждого плагина есть своя собственная директория содержащая файл класса плагина и прочие относящиеся к плагину файлы. Родительский каталог плагина, файл класса плагина, и сам класс должны иметь одно имя. Это очень важно: каталог, имя файла и имя класса полностью идентичны. Рассмотрите следующий пример с плагином HelloWorld т.е.

/cc-content
  /plugins
    /HelloWorld
      HelloWorld.php

        class HelloWorld extends PluginAbstract
        {
          // Код плагина
        }

Установка плагинов

Для установки плагина просто закиньте его папку, содержащую класс и файлы в /cc-content/plugins. Теперь ваш плагин включён в список плагинов раздела (Admin Panel -> Plugins). Список отразит информацию о плагине так, как указано в классе плагина, а также название, автора и статус. Если плагин требует дальнейшей установки, там будет ссылка 'Install', которая запустит для него внутренний установочный процесс. В противном случае просто будет ссылка предлагающая "активировать плагин.

Также возможно установить плагин из .zip архива через страницу Add Plugin административной панели. На этой странице вы можете загрузить плагин с возможностью его автоматического включения/установки, или просто загрузить и оставить выключенным.

Методы плагинов

Плагины могут содержать некоторые методы, распознаваемые CumulusClips, действия которых направлены на сам плагин. Вот эти особенные методы:

Название метода Необходимость Описание
load true Вызывается при каждой загрузке страницы, когда плагин уже загружен.
settings false Обработчик страницы настроек плагина
install false Выполняет пользовательские операции после успешной установки плагина
uninstall false Выполняет пользовательские операции при удалении плагина

Метод load

Метод load вызывается на фазе начальной загрузки при каждом запросе. Тут можно объявить перехватчики любого события в системе. Хотя технически возможно объявить перехватчики в других местах, но конструктор - это реккомендуемое место для объявления перехватчиков событий. Вот пример метода load:

public function load()
{
    // Тут объявляем перехватчики
    Plugin::attachEvent('app.init', array($this, 'myCustomMethod'));
}

Для объявления перехватчика события нужно использовать метод Plugin::attachEvent.

Plugin::attachEvent('EVENT_NAME', array($this, 'INTERNAL_METHOD_NAME'));

Для объявления фильтра события нужно использовать метод Plugin::attachFilter.

Plugin::attachEvent('EVENT_NAME', array($this, 'INTERNAL_METHOD_NAME'));

Метод Plugin::attachEvent принимает два параметра. Первый это название перехватываемого события, второй - название функции или массив, определённый согласно PHP call_user_func функции.

Плагин может включать столько объявлений перехватчиков событий, сколько необходимо. Расположение всех перехватчиков событий в методе load, позволяет любому разработчику быстро увидеть какие события перехватывает плагин. Этот пример показывает готовый метод load с несколькими объявлениями перехватчиков событий:

public function load()
{
    Plugin::attachEvent('app.start', array($this, 'myCustomMethod'));
    Plugin::attachEvent('index.start', array($this, 'customRetrieveVideos'));
    Plugin::attachEvent('index.before_render', array($this, 'CcustomOrderVideos'));
}

Метод settings

Плагины, в необязательном порядке, могут отображать страницу своих собственных настроек. Это может быть использовано, когда плагин имеет параметры, которые могут быть настроены пользователем. Когда в плагине определён публичный метод settings, система включает страницу с настройками для этого плагина и отображает ссылку "Settings" для этого плагина в административной панели.

MyPlugin.php
public function settings()
{
    $this->handleFormRequest();

    echo "<form method="post">"
        . "<label>Setting Name:</label> <input type="text" name="setting_name" value="" />"
        . "<label>Setting Value:</label> <input type="text" name="setting_value" value="" />"
        . "<input type="submit" name="submit" value="Update Plugin Settings" />"
        . "</form>";
}

Это наверняка будет работать, но мы рекомендуем переместить HTML в отдельный файл, т.е. settings_page.html, и подключать его. Наверное, это более чистый подход:

MyPlugin.php
public function settings()
{
    $this->handleFormRequest();

    include('./settings_page.html');
}
settings_page.html
<form method="post">

<label>Setting Name:</label> <input type="text" name="setting_name" value="" />
<label>Setting Value:</label> <input type="text" name="setting_value" value="" />"
<input type="submit" name="submit" value="Update Plugin Settings" />

<form>

Вы можете использовать этот метод, чтобы отобразить страницу настроек с формой для вашего плагина, а также проверки и обработки формы при отправке.

ПРИМЕЧАНИЕ: Ожидается, что метод settings выводит содержимое (напр. echo) напрямую в буфер, а не возвращает его.

Метод install

Плагины, которым надо выполнять какие-либо дополнительные операции при установке могут объявить публичный метод install. Например, это может пригодиться, для внесения изменений в базу данных, создания файлов, изменения файлов и т.п. Метод install вызывается однократно при включении плагина. После того как он был вызван (если он предусмотрен) он больше никогда не будет вызван. До тех пор пока плагин не будет удалён или переустановлен.

Этот метод не является обязательным и может быть опущен. Он исполняется только в процессе включения, если существует. Вот пример метода install:

public function install()
{
    $db = Database::getInstance();
    $query = "INSERT INTO settings (name,value) VALUES ('plugin_setting','setting_value')";
    $db->query($qeury);
}

Метод uninstall

Чтобы отменить какие-либо изменения, произведённые в процессе установки, вы можете использовать метод uninstall. Этот метод вызывается когда плагин удалён через административную панель. Это когда надо, к примеру, удалить таблицы из базы данных или файлы и т.п. Этот метод не обязателен и может быть опущен. Выполняется однократно в процессе удаления плагина.

public function uninstall()
{
    $db = Database::GetInstance();
    $query = "DELETE FROM settings WHERE name LIKE 'custom_plugin%'";
    $db->query($qeury);
}

ПРИМЕЧАНИЕ: Имейте ввиду, что пользователь всегда может физически удалить файл плагина вместо того, чтобы сделать это правильно через административную панель. Такая ситуация может иметь непредвиденные последствия для вас, как для разработчика плагина. Важно, чтобы вы писали свой код так, чтобы он мог справиться с этой ситуацией, если она произойдет.

Пример плагина

Для справки, вот полный плагин. Вы можете скопировать и сохранить его на свой компьютер. Убедитесь, что вы переименовали класс чтобы его имя соответствовало имени файла плагина, а также изменить имя события на то, которое хотите перехватывать.

<?php

class MyPlugin extends PluginAbstract
{
    /**
     * @var string Название плагина
     */
    public $name = 'My Plugin';

    /**
     * @var string Описание плагина
     */
    public $description = 'Sample description';

    /**
     * @var string Имя автора плагина
     */
    public $author = 'CumulusClips';

    /**
     * @var string URL на сайт плагина
     */
    public $url = 'http://cumulusclips.org/';

    /**
     * @var string Текущая версия плагина
     */
    public $version = '1.0.0';

    /**
     * Привязка методов плагина к событиям кода
     */
    public function load()
    {
        Plugin::Attach('event.name', array(__CLASS__, 'myCustomCode'));
    }

    /*
     * Выполнение пользовательского кода
     */
    public function myCustomCode()
    {
         // Plugin code
    }
}