Writing PHP Plugins

This website contains links to software which is either no longer maintained or will be supported only until the end of 2019 (CKFinder 2). For the latest documentation about current CKSource projects, including software like CKEditor 4/CKEditor 5, CKFinder 3, Cloud Services, Letters, Accessibility Checker, please visit the new documentation website.

If you look for an information about very old versions of CKEditor, FCKeditor and CKFinder check also the CKEditor forum, which was closed in 2015. If not, please head to StackOverflow for support.

(Created page with 'CKFinder functionality can be extended with server side plugins. Althought the full source code of CKFinder server connector is available and it can be changed in any way, a much…')
 
Line 34: Line 34:
 
</source>
 
</source>
  
 +
== Adding new server side command ==
 +
 +
Let's write a plugin that adds a new server side command to the connector.
 +
 +
<source lang="php">
 +
<?php
 +
 +
// A simple protection against calling this file directly.
 +
if (!defined('IN_CKFINDER')) exit;
 +
 +
// Include base XML command handler
 +
require_once CKFINDER_CONNECTOR_LIB_DIR . "/CommandHandler/XmlCommandHandlerBase.php";
 +
 +
// Since we will send a XML response, we'll reuse the XmlCommandHandler
 +
class CKFinder_Connector_CommandHandler_FileSize extends CKFinder_Connector_CommandHandler_XmlCommandHandlerBase
 +
{
 +
    // The buildXml method is used to construct an XML response
 +
    function buildXml()
 +
    {
 +
        // A "must have", checking whether the connector is enabled and the basic parameters (like current folder) are safe.
 +
        $this->checkConnector();
 +
        $this->checkRequest();
 +
 +
        // Checking ACL permissions, we're just getting an information about a file, so FILE_VIEW permission seems to be ok.
 +
        if (!$this->_currentFolder->checkAcl(CKFINDER_CONNECTOR_ACL_FILE_VIEW)) {
 +
            $this->_errorHandler->throwError(CKFINDER_CONNECTOR_ERROR_UNAUTHORIZED);
 +
        }
 +
 +
        // Make sure we actually received a file name
 +
        if (!isset($_GET["fileName"])) {
 +
            $this->_errorHandler->throwError(CKFINDER_CONNECTOR_ERROR_INVALID_NAME);
 +
        }
 +
 +
        $fileName = CKFinder_Connector_Utils_FileSystem::convertToFilesystemEncoding($_GET["fileName"]);
 +
        $resourceTypeInfo = $this->_currentFolder->getResourceTypeConfig();
 +
 +
        // Use the resource type configuration object to check whether the extension of a file to check is really allowed.
 +
        if (!$resourceTypeInfo->checkExtension($fileName)) {
 +
            $this->_errorHandler->throwError(CKFINDER_CONNECTOR_ERROR_INVALID_EXTENSION);
 +
        }
 +
 +
        // Make sure that the file name is really ok and has not been sent by hackers
 +
        if (!CKFinder_Connector_Utils_FileSystem::checkFileName($fileName) || $resourceTypeInfo->checkIsHiddenFile($fileName)) {
 +
            $this->_errorHandler->throwError(CKFINDER_CONNECTOR_ERROR_INVALID_REQUEST);
 +
        }
 +
 +
        $filePath = CKFinder_Connector_Utils_FileSystem::combinePaths($this->_currentFolder->getServerPath(), $fileName);
 +
 +
        if (!file_exists($filePath) || !is_file($filePath)) {
 +
            $this->_errorHandler->throwError(CKFINDER_CONNECTOR_ERROR_FILE_NOT_FOUND);
 +
        }
 +
 +
        $size = filesize($filePath);
 +
 +
        $oNode = new Ckfinder_Connector_Utils_XmlNode("FileSize");
 +
        $oNode->addAttribute("size", $size);
 +
        $this->_connectorNode->addChild($oNode);
 +
    }
 +
 +
    function onBeforeExecuteCommand( &$command )
 +
    {
 +
        if ( $command == 'FileSize' )
 +
        {
 +
            $this->sendResponse();
 +
            return false;
 +
        }
 +
 +
        return true ;
 +
    }
 +
}
 +
 +
$CommandHandler_FileSize = new CKFinder_Connector_CommandHandler_FileSize();
 +
$config['Hooks']['BeforeExecuteCommand'][] = array($CommandHandler_FileSize, "onBeforeExecuteCommand");
 +
$config['Plugins'][] = 'dummy';
 +
</source>
 
{{#CUSTOMTITLE:Writing PHP Plugins}}
 
{{#CUSTOMTITLE:Writing PHP Plugins}}

Revision as of 20:56, 17 May 2010

CKFinder functionality can be extended with server side plugins. Althought the full source code of CKFinder server connector is available and it can be changed in any way, a much better way of enhancing CKFinder connector is to create a plugin.

The main advantages of plugins are:

  • Upgrades are much easier.
  • The plugin code is in a single place.
  • Plugins can be easily turned off when are not needed anymore.

Common use cases:

  • Adding new server side command (i.e. fileditor and imageresize plugin).
  • Working with uploaded file (i.e. watermark plugin).
  • Extending the information returned by the Init command (i.e. imageresize plugin).

Creating a plugin

Step1: Create plugin folder

Create a directory for your plugin inside of the "plugins" directory (by default CKFinder comes with three plugins: dummy, fileeditor, imagreresize). Let's use "myplugin" as the plugin name and use the same name for our new folder.

Step2: Create plugin file

Inside of your plugin's folder ("myplugin") create an empty file named plugin.php.

Step3: Add plugin definition

// Let's create an empty PHP file for now

Step4: Enable plugin

Add an include_once/require_once statement in the PHP configuration file (config.php):

include_once "plugins/myplugin/plugin.php";

Adding new server side command

Let's write a plugin that adds a new server side command to the connector.

<?php

// A simple protection against calling this file directly.
if (!defined('IN_CKFINDER')) exit;

// Include base XML command handler
require_once CKFINDER_CONNECTOR_LIB_DIR . "/CommandHandler/XmlCommandHandlerBase.php";

// Since we will send a XML response, we'll reuse the XmlCommandHandler
class CKFinder_Connector_CommandHandler_FileSize extends CKFinder_Connector_CommandHandler_XmlCommandHandlerBase
{
    // The buildXml method is used to construct an XML response
    function buildXml()
    {
        // A "must have", checking whether the connector is enabled and the basic parameters (like current folder) are safe.
        $this->checkConnector();
        $this->checkRequest();

        // Checking ACL permissions, we're just getting an information about a file, so FILE_VIEW permission seems to be ok.
        if (!$this->_currentFolder->checkAcl(CKFINDER_CONNECTOR_ACL_FILE_VIEW)) {
            $this->_errorHandler->throwError(CKFINDER_CONNECTOR_ERROR_UNAUTHORIZED);
        }

        // Make sure we actually received a file name
        if (!isset($_GET["fileName"])) {
            $this->_errorHandler->throwError(CKFINDER_CONNECTOR_ERROR_INVALID_NAME);
        }

        $fileName = CKFinder_Connector_Utils_FileSystem::convertToFilesystemEncoding($_GET["fileName"]);
        $resourceTypeInfo = $this->_currentFolder->getResourceTypeConfig();

        // Use the resource type configuration object to check whether the extension of a file to check is really allowed.
        if (!$resourceTypeInfo->checkExtension($fileName)) {
            $this->_errorHandler->throwError(CKFINDER_CONNECTOR_ERROR_INVALID_EXTENSION);
        }

        // Make sure that the file name is really ok and has not been sent by hackers
        if (!CKFinder_Connector_Utils_FileSystem::checkFileName($fileName) || $resourceTypeInfo->checkIsHiddenFile($fileName)) {
            $this->_errorHandler->throwError(CKFINDER_CONNECTOR_ERROR_INVALID_REQUEST);
        }

        $filePath = CKFinder_Connector_Utils_FileSystem::combinePaths($this->_currentFolder->getServerPath(), $fileName);

        if (!file_exists($filePath) || !is_file($filePath)) {
            $this->_errorHandler->throwError(CKFINDER_CONNECTOR_ERROR_FILE_NOT_FOUND);
        }

        $size = filesize($filePath);

        $oNode = new Ckfinder_Connector_Utils_XmlNode("FileSize");
        $oNode->addAttribute("size", $size);
        $this->_connectorNode->addChild($oNode);
    }

    function onBeforeExecuteCommand( &$command )
    {
        if ( $command == 'FileSize' )
        {
            $this->sendResponse();
            return false;
        }

        return true ;
    }
}

$CommandHandler_FileSize = new CKFinder_Connector_CommandHandler_FileSize();
$config['Hooks']['BeforeExecuteCommand'][] = array($CommandHandler_FileSize, "onBeforeExecuteCommand");
$config['Plugins'][] = 'dummy';