Writing ASP 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 '__TOC__{{CKFinder 2.x Writing Plugins Introduction}} == Creating a plugin == ==== Step1: Create plugin folder ==== Create a directory for your plugin inside of the "plugins" di…')
 
(Enabling JavaScript plugin)
 
(12 intermediate revisions by the same user not shown)
Line 8: Line 8:
 
==== Step2: Create plugin file ====
 
==== Step2: Create plugin file ====
  
Inside of your plugin's folder ("myplugin") create an empty file named '''plugin.php'''.
+
Inside of your plugin's folder ("myplugin") create an empty file named '''plugin.asp'''.
  
 
==== Step3: Add plugin definition ====
 
==== Step3: Add plugin definition ====
  
// Let's create an empty PHP file for now
+
// Let's create an empty ASP file for now
  
 
==== Step4: Enable plugin ====
 
==== Step4: Enable plugin ====
  
Add an include_once/require_once statement in the PHP configuration file (config.php):  
+
Add an INCLUDE statement in the ASP configuration file (config.asp):  
  
<source lang="php">
+
<source lang="asp">
include_once "plugins/myplugin/plugin.php";
+
<!-- #INCLUDE file="plugins/myplugin/plugin.asp" -->
 
</source>
 
</source>
  
== PHP plugin system ==
+
== ASP plugin system ==
  
 
=== Hooks ===
 
=== Hooks ===
Line 28: Line 28:
 
CKFinder provides several hooks that can be used to extend the functionality of the CKFinder application. Assigning a function (also known as an event handler) to a hook will cause that function to be called at the appropriate point in the main CKFinder code, to perform whatever additional task(s) the developer thinks would be useful at that point. Each hook can have multiple handlers assigned to it, in which case it will call the functions in the order that they are assigned.
 
CKFinder provides several hooks that can be used to extend the functionality of the CKFinder application. Assigning a function (also known as an event handler) to a hook will cause that function to be called at the appropriate point in the main CKFinder code, to perform whatever additional task(s) the developer thinks would be useful at that point. Each hook can have multiple handlers assigned to it, in which case it will call the functions in the order that they are assigned.
  
Hooks should be assigned in a plugin file. The easiest way to assign a function to a hook is:
+
Hooks should be assigned in a plugin file. To assign a event listener to a hook call:
<source lang="php">
+
<source lang="asp">
$config['Hooks']['event'][] = 'function';
+
CKFinder_AddHook "EventName", CommandHandler
</source>
 
 
 
However, usually you'll provide a class instance and a method name.
 
 
 
<source lang="php">
 
// Resulting function call: $object->someMethod($param1, $param2);
 
$config['Hooks']['event'][] = array($object, 'someMethod');
 
 
</source>
 
</source>
 +
where EventName is the name of a hook and CommandHandler is an object that contains a method named '''On'''EventName.
  
 
==== Available hooks ====
 
==== Available hooks ====
Line 45: Line 39:
 
=== Enabling JavaScript plugin ===
 
=== Enabling JavaScript plugin ===
  
Sometimes a server side plugin might come with a client side (JavaScript) plugin, that should be automatically enabled when the server side plugin is enabled.<br>
+
Sometimes a server side plugin might come with a client side (JavaScript) plugin, that should be automatically enabled when the server side plugin is enabled. To enable a JavaScript plugin inside your ASP plugin, use <code>CKFinder_AddPlugin</code> function.
The <code>$config['Plugins']</code> variable is a special array that does that.
 
  
To enable a plugin, simply add it's name to this array.
+
To enable a plugin, simply call CKFinder_AddPlugin.
<source lang="php">
+
<source lang="asp">
$config['Plugins'][] = 'myplugin';
+
CKFinder_AddPlugin "myplugin"
 
</source>
 
</source>
  
Line 57: Line 50:
 
config.extraPlugins = 'myplugin';
 
config.extraPlugins = 'myplugin';
 
</source>
 
</source>
but the advantage of defining it in plugin.php is that it will be enabled only when the server side plugin is also enabled.
+
but the advantage of defining it in plugin.asp is that it will be enabled only when the server side plugin is also enabled.
 
 
{{CKFinder_2.x Sample Plugin Introduction|ext=php}}
 
 
 
For the sake of simplicity, we'll first create a simple '''plugin.php''' that just does exactly what we need:
 
<source lang="php">
 
<?php
 
  
// (2) Include base XML command handler
+
{{CKFinder_2.x Sample Plugin Introduction|ext=asp}}
require_once CKFINDER_CONNECTOR_LIB_DIR . "/CommandHandler/XmlCommandHandlerBase.php";
 
  
// Since we will send a XML response, we'll extend the XmlCommandHandlerBase
+
For the sake of simplicity, we'll first create a simple '''plugin.asp''' that just does exactly what we need:
class CKFinder_Connector_CommandHandler_FileSize extends CKFinder_Connector_CommandHandler_XmlCommandHandlerBase
+
<source lang="asp">
{
+
<script runat="server" language="VBScript">
    // (4) The buildXml method is used to construct an XML response
 
    function buildXml()
 
    {
 
        $fileName = $_GET["fileName"];
 
        $filePath = CKFinder_Connector_Utils_FileSystem::combinePaths($this->_currentFolder->getServerPath(), $fileName);
 
  
         // (5) Adding a <FileSize> element to the XML response.
+
' (2)
         $oNode = new Ckfinder_Connector_Utils_XmlNode("FileSize");
+
class CKFinder_Connector_CommandHandler_FileSize
         $oNode->addAttribute("size", filesize($filePath));
+
    ' Pseudo inheritance
        $this->_connectorNode->addChild($oNode);
+
    private base
     }
+
 
+
    ' (2) Since we want to send a XML response, we'll extend the XmlCommandHandlerBase class
     // (3) Register the "FileSize" command
+
    Private Sub Class_Initialize()
     function onBeforeExecuteCommand( &$command )
+
        Set base = new CKFinder_Connector_CommandHandler_XmlCommandHandlerBase
    {
+
        Set base.child = me
         if ( $command == 'FileSize' )
+
    End Sub
        {
+
             // The sendResponse method is defined in XmlCommandHandlerBase, it creates  
+
    ' Pseudo inheritance
             // a basic XML response and calls the buildXml()method  
+
    Public Property Get currentFolder()
             $this->sendResponse();
+
        Set currentFolder = base.currentFolder
             // false = stop further execution.
+
    End Property
             return false;
+
         }
+
    Public Sub sendResponse(response)
 
+
        base.sendResponse(response)
         return true ;
+
    End sub
     }
+
}
+
    Public Property Get ErrorHandler()
 
+
        Set ErrorHandler = base.ErrorHandler
$CommandHandler_FileSize = new CKFinder_Connector_CommandHandler_FileSize();
+
    End Property
// (1) Register the onBeforeExecuteCommand method to be called by the BeforeExecuteCommand hook.
+
$config['Hooks']['BeforeExecuteCommand'][] = array($CommandHandler_FileSize, "onBeforeExecuteCommand");
+
    ' (4) The buildXml method is used to construct an XML response
 +
    function buildXml( oXML )
 +
        Dim fileName
 +
        fileName = request("fileName")
 +
 +
        Dim oUFS
 +
        Set oUFS = oCKFinder_Factory.UtilsFileSystem
 +
 +
        Dim filePath
 +
        filePath = oUFS.combinePaths(currentFolder.getServerPath(), fileName)
 +
 +
         ' (5) Adding a <FileSize> element to the XML response.
 +
         Dim size, oNode
 +
        size = oUFS.GetFileSize(filePath)
 +
        Set oNode = oXML.connectorNode.addChild("FileSize")
 +
         oNode.addAttribute "size", size
 +
 +
     End function
 +
 +
    ' Our event listener:
 +
     ' (3) Register the "FileSize" command
 +
     public function onBeforeExecuteCommand( command )
 +
         if ( command = "FileSize" ) then
 +
             ' The sendResponse method is defined in XmlCommandHandlerBase, it creates  
 +
             ' a basic XML response and calls the buildXml()method  
 +
             sendResponse( response )
 +
             ' false = stop further execution.
 +
             onBeforeExecuteCommand = False
 +
            Exit function
 +
         End if
 +
 +
         onBeforeExecuteCommand = True
 +
     End Function
 +
 +
End Class
 +
 +
Dim CommandHandler_FileSize
 +
Set CommandHandler_FileSize = new CKFinder_Connector_CommandHandler_FileSize
 +
 +
' (1) Object assigned to a hook must contain event listener named "onEventName"
 +
' (the event name is BeforeExecuteCommand, so we must define an onBeforeExecuteCommand method).
 +
CKFinder_AddHook "BeforeExecuteCommand", CommandHandler_FileSize
 +
CKFinder_AddPlugin "myplugin"
 +
 +
</script>
 
</source>
 
</source>
  
 
==== Step1: Register an event handler ====
 
==== Step1: Register an event handler ====
<source lang="php">
+
<source lang="asp">
$config['Hooks']['BeforeExecuteCommand'][] = array($CommandHandler_FileSize, "onBeforeExecuteCommand");
+
CKFinder_AddHook "BeforeExecuteCommand", CommandHandler_FileSize
 
</source>
 
</source>
  
 
==== Step2: Create a class ====
 
==== Step2: Create a class ====
 
If your plugin returns an XML response, you'll usually just extend the XmlCommandHandlerBase class to reduce the amount of code to write, however it is not a requirement.
 
If your plugin returns an XML response, you'll usually just extend the XmlCommandHandlerBase class to reduce the amount of code to write, however it is not a requirement.
<source lang="php">
+
<source lang="asp">
// (2) Include base XML command handler
+
class CKFinder_Connector_CommandHandler_FileSize
require_once CKFINDER_CONNECTOR_LIB_DIR . "/CommandHandler/XmlCommandHandlerBase.php";
+
' Pseudo inheritance
 +
private base
 +
 +
' Since we want to send a XML response, we'll extend the XmlCommandHandlerBase class
 +
Private Sub Class_Initialize()
 +
Set base = new CKFinder_Connector_CommandHandler_XmlCommandHandlerBase
 +
Set base.child = me
 +
End Sub
 +
 
 +
' ...
  
// Since we will send a XML response, we'll extend the XmlCommandHandlerBase
+
End Class
class CKFinder_Connector_CommandHandler_FileSize extends CKFinder_Connector_CommandHandler_XmlCommandHandlerBase
 
 
</source>
 
</source>
  
 
==== Step3: Create an event handler ====
 
==== Step3: Create an event handler ====
Our event handler defined in (1) is called "onBeforeExecuteCommand", so let's define such function.
+
Our event handler defined in (1) should be called "OnBeforeExecuteCommand", so let's define such function.
<source lang="php">
+
<source lang="asp">
function onBeforeExecuteCommand( &$command )
+
public function onBeforeExecuteCommand( command )
// ...
+
' ...
 
</source>
 
</source>
  
Line 129: Line 162:
 
In the <code>onBeforeExecuteCommand</code> method we have called <code>sendResponse</code>. The <code>sendResponse method is defined</code> in XmlCommandHandlerBase class, it creates a basic XML response and calls the <code>buildXml</code> method, which we need to define.
 
In the <code>onBeforeExecuteCommand</code> method we have called <code>sendResponse</code>. The <code>sendResponse method is defined</code> in XmlCommandHandlerBase class, it creates a basic XML response and calls the <code>buildXml</code> method, which we need to define.
 
<source lang="php">
 
<source lang="php">
function buildXml()
+
function buildXml( oXML )
// ...
+
' ...
 
</source>
 
</source>
  
 
==== Step5: Construct the XML response ====
 
==== Step5: Construct the XML response ====
 
The main task of the buildXml method is to construct an XML response, so we're doing it below:  
 
The main task of the buildXml method is to construct an XML response, so we're doing it below:  
<source lang="php">
+
<source lang="asp">
$oNode = new Ckfinder_Connector_Utils_XmlNode("FileSize");
+
Dim size, oNode
$oNode->addAttribute("size", $size);
+
size = oUFS.GetFileSize(filePath)
$this->_connectorNode->addChild($oNode);
+
Set oNode = oXML.connectorNode.addChild("FileSize")
 +
oNode.addAttribute "size", size
 
</source>
 
</source>
  
 
==== Full source code ====
 
==== Full source code ====
===== plugin.php =====
+
===== plugin.asp =====
The full source code of a plugin with all necessary security checks: (save the code as '''plugin.php''' in "plugins/myplugin" folder)
+
The full source code of a plugin with all necessary security checks: (save the code as '''plugin.asp''' in "plugins/myplugin" folder)
  
<source lang="php">
+
<source lang="asp">
<?php
+
<script runat="server" language="VBScript">
 +
 
 +
' (2)
 +
class CKFinder_Connector_CommandHandler_FileSize
 +
    ' Pseudo inheritance
 +
    private base
 +
 
 +
    ' (2) Since we want to send a XML response, we'll extend the XmlCommandHandlerBase class
 +
    Private Sub Class_Initialize()
 +
        Set base = new CKFinder_Connector_CommandHandler_XmlCommandHandlerBase
 +
        Set base.child = me
 +
    End Sub
 +
 
 +
    Private Sub Class_Terminate()
 +
        Set base.child = Nothing
 +
        Set base = Nothing
 +
    End Sub
 +
 
 +
    ' Pseudo inheritance
 +
    Public Property Get currentFolder()
 +
        Set currentFolder = base.currentFolder
 +
    End Property
 +
 
 +
    Public Sub sendResponse(response)
 +
        base.sendResponse(response)
 +
    End sub
 +
 
 +
    Public Property Get ErrorHandler()
 +
        Set ErrorHandler = base.ErrorHandler
 +
    End Property
 +
 
 +
    ' (4) The buildXml method is used to construct an XML response
 +
    function buildXml( oXML )
 +
 
 +
        if not(currentFolder.checkAcl(CKFINDER_CONNECTOR_ACL_FILE_VIEW)) then
 +
            errorHandler.throwError CKFINDER_CONNECTOR_ERROR_UNAUTHORIZED, "", "ACL check failed"
 +
        End if
  
// A simple protection against calling this file directly.
+
        Dim resourceTypeInfo
if (!defined('IN_CKFINDER')) exit;
+
        Set resourceTypeInfo = currentFolder.getResourceTypeConfig()
  
// Include base XML command handler
+
        Dim fileName
require_once CKFINDER_CONNECTOR_LIB_DIR . "/CommandHandler/XmlCommandHandlerBase.php";
+
        fileName = request("fileName")
 +
        If (fileName="") then
 +
            errorHandler.throwError CKFINDER_CONNECTOR_ERROR_INVALID_NAME, "", "Missing filename"
 +
        End if
  
// Since we will send a XML response, we'll reuse the XmlCommandHandler
+
        Dim oUFS
class CKFinder_Connector_CommandHandler_FileSize extends CKFinder_Connector_CommandHandler_XmlCommandHandlerBase
+
         Set oUFS = oCKFinder_Factory.UtilsFileSystem
{
 
    // 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 (Not oUFS.checkFileName(fileName) or resourceTypeInfo.checkIsHiddenFile(fileName)) then
         if (!$this->_currentFolder->checkAcl(CKFINDER_CONNECTOR_ACL_FILE_VIEW)) {
+
             errorHandler.throwError CKFINDER_CONNECTOR_ERROR_INVALID_REQUEST, "", "Invalid filename"
             $this->_errorHandler->throwError(CKFINDER_CONNECTOR_ERROR_UNAUTHORIZED);
+
         End if
         }
 
  
        // Make sure we actually received a file name
+
         if (Not resourceTypeInfo.checkExtension(fileName)) then
         if (!isset($_GET["fileName"])) {
+
            errorHandler.throwError CKFINDER_CONNECTOR_ERROR_INVALID_REQUEST, "", "Invalid extension"
            $this->_errorHandler->throwError(CKFINDER_CONNECTOR_ERROR_INVALID_NAME);
+
         End if
         }
 
  
         $fileName = CKFinder_Connector_Utils_FileSystem::convertToFilesystemEncoding($_GET["fileName"]);
+
         Dim filePath
         $resourceTypeInfo = $this->_currentFolder->getResourceTypeConfig();
+
         filePath = oUFS.combinePaths(currentFolder.getServerPath(), fileName)
  
         // Use the resource type configuration object to check whether the extension of a file to check is really allowed.
+
         If Not(oUFS.fileExists(filePath)) then
        if (!$resourceTypeInfo->checkExtension($fileName)) {
+
            errorHandler.throwError CKFINDER_CONNECTOR_ERROR_FILE_NOT_FOUND, "", "File doesn't exists: " & filePath
            $this->_errorHandler->throwError(CKFINDER_CONNECTOR_ERROR_INVALID_EXTENSION);
+
         End if
         }
 
  
         // Make sure that the file name is really ok and has not been sent by a hacker
+
         ' (5) Adding a <FileSize> element to the XML response.
         if (!CKFinder_Connector_Utils_FileSystem::checkFileName($fileName) || $resourceTypeInfo->checkIsHiddenFile($fileName)) {
+
        Dim size, oNode
            $this->_errorHandler->throwError(CKFINDER_CONNECTOR_ERROR_INVALID_REQUEST);
+
         size = oUFS.GetFileSize(filePath)
         }
+
        Set oNode = oXML.connectorNode.addChild("FileSize")
 +
         oNode.addAttribute "size", size
  
        $filePath = CKFinder_Connector_Utils_FileSystem::combinePaths($this->_currentFolder->getServerPath(), $fileName);
+
    End function
  
         if (!file_exists($filePath) || !is_file($filePath)) {
+
    ' Our event listener:
            $this->_errorHandler->throwError(CKFINDER_CONNECTOR_ERROR_FILE_NOT_FOUND);
+
    ' (3) Register the "FileSize" command
         }
+
    public function onBeforeExecuteCommand( command )
 +
         if ( command = "FileSize" ) then
 +
' The sendResponse method is defined in XmlCommandHandlerBase, it creates
 +
' a basic XML response and calls the buildXml()method
 +
sendResponse( response )
 +
' false = stop further execution.
 +
onBeforeExecuteCommand = False
 +
Exit function
 +
         End if
  
         $size = filesize($filePath);
+
         onBeforeExecuteCommand = True
 +
    End Function
  
        // *** The main part of this plugin ****
+
End Class
        // Adding a <FileSize> element to the XML response.
 
        $oNode = new Ckfinder_Connector_Utils_XmlNode("FileSize");
 
        $oNode->addAttribute("size", $size);
 
        $this->_connectorNode->addChild($oNode);
 
    }
 
  
    // Register the "FileSize" command
+
Dim CommandHandler_FileSize
    function onBeforeExecuteCommand( &$command )
+
If (TypeName(oCKFinder_Factory) <> "Empty") then
    {
+
    Set CommandHandler_FileSize = new CKFinder_Connector_CommandHandler_FileSize
        if ( $command == 'FileSize' )
 
        {
 
            // The sendResponse method is defined in XmlCommandHandlerBase, it creates
 
            // a basic XML response and calls the buildXml()method
 
            $this->sendResponse();
 
            // false = stop further execution.
 
            return false;
 
        }
 
  
        return true ;
+
    ' (1) Object assigned to a hook must contain event listener named "onEventName"
     }
+
    ' (the event name is BeforeExecuteCommand, so we must define an onBeforeExecuteCommand method).
}
+
    CKFinder_AddHook "BeforeExecuteCommand", CommandHandler_FileSize
 +
     CKFinder_AddPlugin "myplugin"
 +
End if
  
$CommandHandler_FileSize = new CKFinder_Connector_CommandHandler_FileSize();
+
</script>
// Register the onBeforeExecuteCommand method to be called by the BeforeExecuteCommand hook.
 
$config['Hooks']['BeforeExecuteCommand'][] = array($CommandHandler_FileSize, "onBeforeExecuteCommand");
 
// (Optional) Register a javascript plugin named "myplugin"
 
$config['Plugins'][] = 'myplugin';
 
 
</source>
 
</source>
  
 
{{CKFinder_2.x myplugin code}}
 
{{CKFinder_2.x myplugin code}}
 
{{#CUSTOMTITLE:Writing ASP Plugins}}
 
{{#CUSTOMTITLE:Writing ASP Plugins}}

Latest revision as of 09:05, 26 May 2010

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

The main advantages of plugins are:

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

Common use cases:

  • Adding a new server-side command (i.e. fileditor and imageresize plugin).
  • Working with uploaded files (i.e. watermark plugin).
  • Extending 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.asp.

Step3: Add plugin definition

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

Step4: Enable plugin

Add an INCLUDE statement in the ASP configuration file (config.asp):

<!-- #INCLUDE file="plugins/myplugin/plugin.asp" -->

ASP plugin system

Hooks

CKFinder provides several hooks that can be used to extend the functionality of the CKFinder application. Assigning a function (also known as an event handler) to a hook will cause that function to be called at the appropriate point in the main CKFinder code, to perform whatever additional task(s) the developer thinks would be useful at that point. Each hook can have multiple handlers assigned to it, in which case it will call the functions in the order that they are assigned.

Hooks should be assigned in a plugin file. To assign a event listener to a hook call:

CKFinder_AddHook "EventName", CommandHandler

where EventName is the name of a hook and CommandHandler is an object that contains a method named OnEventName.

Available hooks

Hook Since Description
AfterFileUpload 2.0 Executed after successful file upload.
BeforeExecuteCommand 2.0 Executed before a server side command is executed.
InitCommand 2.0 Executed straight before sending the result of the Init command.

Enabling JavaScript plugin

Sometimes a server side plugin might come with a client side (JavaScript) plugin, that should be automatically enabled when the server side plugin is enabled. To enable a JavaScript plugin inside your ASP plugin, use CKFinder_AddPlugin function.

To enable a plugin, simply call CKFinder_AddPlugin.

CKFinder_AddPlugin "myplugin"

This code is virtually equal to specyfying in config.js:

config.extraPlugins = 'myplugin';

but the advantage of defining it in plugin.asp is that it will be enabled only when the server side plugin is also enabled.

Sample plugin: FileSize (adding new server side command - complete example)

Introduction

Probably the best way to learn new things is to write a code, so let's write a plugin that adds a new server side command to the connector. We'll create a command that returns a size of a given file.

If you're unfamiliar with CKFinder architecture, please take a look at Server Side Integration documentation. Alternatively, just bear in mind that CKFinder is an AJAX application and that the connection between the user interface running in a browser and the server connector is simply made of AJAX calls to the connector. Check AJAX calls in Firebug to better understand CKFinder.

The FileSize plugin should provide a new command named "FileSize", in other words, calling:

/ckfinder/core/connector/asp/connector.asp?command=FileSize&type=Files&currentFolder=%2F&fileName=foobar.jpg

(assuming that foobar.jpg exists) should return a valid XML response:

<Connector resourceType="Files">
<Error number="0"/>
<CurrentFolder path="/" url="/ckfinder/userfiles/files/" acl="255"/>
<FileSize size="5647"/>
</Connector>

For the sake of simplicity, we'll first create a simple plugin.asp that just does exactly what we need:

<script runat="server" language="VBScript">

' (2)
class CKFinder_Connector_CommandHandler_FileSize
    ' Pseudo inheritance
    private base
 
    ' (2) Since we want to send a XML response, we'll extend the XmlCommandHandlerBase class
    Private Sub Class_Initialize()
        Set base = new CKFinder_Connector_CommandHandler_XmlCommandHandlerBase
        Set base.child = me
    End Sub
 
    ' Pseudo inheritance
    Public Property Get currentFolder()
        Set currentFolder = base.currentFolder
    End Property
 
    Public Sub sendResponse(response)
        base.sendResponse(response)
    End sub
 
    Public Property Get ErrorHandler()
        Set ErrorHandler = base.ErrorHandler
    End Property
 
    ' (4) The buildXml method is used to construct an XML response
    function buildXml( oXML )
        Dim fileName
        fileName = request("fileName")
 
        Dim oUFS
        Set oUFS = oCKFinder_Factory.UtilsFileSystem
 
        Dim filePath
        filePath = oUFS.combinePaths(currentFolder.getServerPath(), fileName)
 
        ' (5) Adding a <FileSize> element to the XML response.
        Dim size, oNode
        size = oUFS.GetFileSize(filePath)
        Set oNode = oXML.connectorNode.addChild("FileSize")
        oNode.addAttribute "size", size
 
    End function
 
    ' Our event listener:
    ' (3) Register the "FileSize" command
    public function onBeforeExecuteCommand( command )
        if ( command = "FileSize" ) then
            ' The sendResponse method is defined in XmlCommandHandlerBase, it creates 
            ' a basic XML response and calls the buildXml()method 
            sendResponse( response )
            ' false = stop further execution.
            onBeforeExecuteCommand = False
            Exit function
        End if
 
        onBeforeExecuteCommand = True
    End Function
 
End Class
 
Dim CommandHandler_FileSize
Set CommandHandler_FileSize = new CKFinder_Connector_CommandHandler_FileSize
 
' (1) Object assigned to a hook must contain event listener named "onEventName"
' (the event name is BeforeExecuteCommand, so we must define an onBeforeExecuteCommand method).
CKFinder_AddHook "BeforeExecuteCommand", CommandHandler_FileSize
CKFinder_AddPlugin "myplugin"
 
</script>

Step1: Register an event handler

CKFinder_AddHook "BeforeExecuteCommand", CommandHandler_FileSize

Step2: Create a class

If your plugin returns an XML response, you'll usually just extend the XmlCommandHandlerBase class to reduce the amount of code to write, however it is not a requirement.

class CKFinder_Connector_CommandHandler_FileSize
	' Pseudo inheritance
	private base
 
	' Since we want to send a XML response, we'll extend the XmlCommandHandlerBase class
	Private Sub Class_Initialize()
		Set base = new CKFinder_Connector_CommandHandler_XmlCommandHandlerBase
		Set base.child = me
	End Sub

	' ...

End Class

Step3: Create an event handler

Our event handler defined in (1) should be called "OnBeforeExecuteCommand", so let's define such function.

public function onBeforeExecuteCommand( command )
' ...

Step4: Create the buildXml method

In the onBeforeExecuteCommand method we have called sendResponse. The sendResponse method is defined in XmlCommandHandlerBase class, it creates a basic XML response and calls the buildXml method, which we need to define.

function buildXml( oXML )
' ...

Step5: Construct the XML response

The main task of the buildXml method is to construct an XML response, so we're doing it below:

Dim size, oNode
size = oUFS.GetFileSize(filePath)
Set oNode = oXML.connectorNode.addChild("FileSize")
oNode.addAttribute "size", size

Full source code

plugin.asp

The full source code of a plugin with all necessary security checks: (save the code as plugin.asp in "plugins/myplugin" folder)

<script runat="server" language="VBScript">

' (2)
class CKFinder_Connector_CommandHandler_FileSize
    ' Pseudo inheritance
    private base

    ' (2) Since we want to send a XML response, we'll extend the XmlCommandHandlerBase class
    Private Sub Class_Initialize()
        Set base = new CKFinder_Connector_CommandHandler_XmlCommandHandlerBase
        Set base.child = me
    End Sub

    Private Sub Class_Terminate()
        Set base.child = Nothing
        Set base = Nothing
    End Sub

    ' Pseudo inheritance
    Public Property Get currentFolder()
        Set currentFolder = base.currentFolder
    End Property

    Public Sub sendResponse(response)
        base.sendResponse(response)
    End sub

    Public Property Get ErrorHandler()
        Set ErrorHandler = base.ErrorHandler
    End Property

    ' (4) The buildXml method is used to construct an XML response
    function buildXml( oXML )

        if not(currentFolder.checkAcl(CKFINDER_CONNECTOR_ACL_FILE_VIEW)) then
            errorHandler.throwError CKFINDER_CONNECTOR_ERROR_UNAUTHORIZED, "", "ACL check failed"
        End if

        Dim resourceTypeInfo
        Set resourceTypeInfo = currentFolder.getResourceTypeConfig()

        Dim fileName
        fileName = request("fileName")
        If (fileName="") then
            errorHandler.throwError CKFINDER_CONNECTOR_ERROR_INVALID_NAME, "", "Missing filename"
        End if

        Dim oUFS
        Set oUFS = oCKFinder_Factory.UtilsFileSystem

        if (Not oUFS.checkFileName(fileName) or resourceTypeInfo.checkIsHiddenFile(fileName)) then
            errorHandler.throwError CKFINDER_CONNECTOR_ERROR_INVALID_REQUEST, "", "Invalid filename"
        End if

        if (Not resourceTypeInfo.checkExtension(fileName)) then
             errorHandler.throwError CKFINDER_CONNECTOR_ERROR_INVALID_REQUEST, "", "Invalid extension"
        End if

        Dim filePath
        filePath = oUFS.combinePaths(currentFolder.getServerPath(), fileName)

        If Not(oUFS.fileExists(filePath)) then
             errorHandler.throwError CKFINDER_CONNECTOR_ERROR_FILE_NOT_FOUND, "", "File doesn't exists: " & filePath
        End if

        ' (5) Adding a <FileSize> element to the XML response.
        Dim size, oNode
        size = oUFS.GetFileSize(filePath)
        Set oNode = oXML.connectorNode.addChild("FileSize")
        oNode.addAttribute "size", size

    End function

    ' Our event listener:
    ' (3) Register the "FileSize" command
    public function onBeforeExecuteCommand( command )
        if ( command = "FileSize" ) then
			' The sendResponse method is defined in XmlCommandHandlerBase, it creates 
			' a basic XML response and calls the buildXml()method 
			sendResponse( response )
				' false = stop further execution.
			onBeforeExecuteCommand = False
			Exit function
        End if

        onBeforeExecuteCommand = True
    End Function

End Class

Dim CommandHandler_FileSize
If (TypeName(oCKFinder_Factory) <> "Empty") then
    Set CommandHandler_FileSize = new CKFinder_Connector_CommandHandler_FileSize

    ' (1) Object assigned to a hook must contain event listener named "onEventName"
    ' (the event name is BeforeExecuteCommand, so we must define an onBeforeExecuteCommand method).
    CKFinder_AddHook "BeforeExecuteCommand", CommandHandler_FileSize
    CKFinder_AddPlugin "myplugin"
End if

</script>
plugin.js

.. and the client side (JavaScript) plugin that will call the FileSize command: (save the code as plugin.js in "plugins/myplugin" folder)

CKFinder.addPlugin( 'myplugin', function( api ) {
	api.addFileContextMenuOption( { label : 'File Size', command : "FileSize" } , function( api, file )
	{
		api.connector.sendCommand( 'FileSize', { fileName : api.getSelectedFile().name }, function( xml )
		{
			if ( xml.checkError() )
				return;

			var size = xml.selectSingleNode( 'Connector/FileSize/@size' );
			api.openMsgDialog( "", "The exact size of a file is: " + size.value + " bytes");
		} );
	});
});

This page was last edited on 26 May 2010, at 09:05.