Mastering Joomla! 1.5 Extension and Framework Development phần 4 pps

48 772 0
Mastering Joomla! 1.5 Extension and Framework Development phần 4 pps

Đang tải... (xem toàn văn)

Tài liệu hạn chế xem trước, để xem đầy đủ mời bạn chọn Tải xuống

Thông tin tài liệu

Chapter 5 [ 131 ] Summary The two avors in which modules come, frontend and backend, essentially dene two different types of extension. Backend modules are often overlooked because we tend to be less aware of them. We should try to remember that backend modules are very powerful and can greatly enhance the administrative capabilities of components. Modules are integral to the success of a component. It's not uncommon for one component to include several modules. The simple nature of modules makes it easy to become sophisticated about them. It's important to remember that because they are used and rendered so frequently, efcient code is essential to good module design. Plugin Design Plugins enable us to modify system functionality without the need to alter existing code. For example, plugins can be used to alter content before it is displayed, extend search functionality, or implement a custom authentication mechanism. As an example, this chapter shows how to replace a string in an article with an image. Plugins use the Observer pattern to keep an eye on events. It is by listening to these events that we can modify the system functionality. However, this also means that we are limited to only modifying those parts of the system that raise events. Plugins represent the listener, and they can dene either a listener class or a listener function to handle specic events. In this chapter, we will cover the following: Setting up a Sandbox Events Listeners Plugin Groups Loading Plugins Using Plugins as libraries (in lieu of library extensions) Translating Plugins Dealing with Plugin Settings (Parameters) Packaging File Naming Conicts • • • • • • • • • • Plugin Design [ 134 ] Setting Up a Sandbox When we start building a new plugin it is imperative that we have a sandbox: somewhere we can test our code. Ideally, we should have more than one system so we can test our plugins on different server setups. To set up a plugin sandbox we can create a basic installer. The XML displayed below can be used to create a blank plugin called 'Foobar - My Extension'. <?xml version="1.0" encoding="utf-8"?> <!DOCTYPE install SYSTEM "http://dev.joomla.org/xml/1.5/plugin-install.dtd"> <install version="1.5" type="plugin" group="foobar"> <name>Foobar - My Extension</name> <author>Author's Name</author> <authorEmail>Author's Email</authorEmail> <authorUrl>Author's Website</authorUrl> <creationDate>MonthName Year</creationDate> <copyright>Copyright Notice</copyright> <license>Plugin License Agreement</license> <version>Plugin Version</version> <description>Plugin Description</description> <files> <filename plugin="myextension">myextension.php</filename> </files> <params/> </install> To use this, create a new XML manifest le, using UTF-8 encoding, and save the above code into it. You should update the XML to suit the plugin you intend to build. One of the most important pieces of information in this le is the group attribute of the install tag. Plugins are organized into logical groups. This list details the core groups: authentication content editors editors-xtd search system user xmlrpc • • • • • • • • Chapter 6 [ 135 ] We can use other groups as well. For example, the group in our XML is foobar. It may seem slightly obscure, but another piece of important information in the XML is the filename tag plugin parameter. This parameter identies the plugin element. The element is a unique identier used to determine the root plugin le and used as part of the naming convention. Be careful when you select an element name for your plugin. Only one plugin per group may use any one element name. This table details reserved plugin element names (used by the core): Group Reserved element name authentication gmail joomla ldap openid content emailcloak geshi loadmodule pagebreak pagenavigation sef vote editors none tinymce xstandard editors-xtd image pagebreak readmore search categories contacts content newsfeeds sections weblinks system cache debug legacy Plugin Design [ 136 ] Group Reserved element name system log remember user joomla xmlrpc blogger joomla Once you have built your XML manifest le, create a new PHP le named after the plugin element; this is the le that is invoked when the plugin is loaded. For example, you would have to name the le myextension.php if you were to use the XML displayed above. If you do not include this le, you will not be able to install the plugin. Now create a new archive, it can be gz, .tar, .tar.gz, or zip, and add the XML manifest le and PHP le to it. If you install the archive, you should get a blank plugin, which you can begin to develop. Plugins are not stored in separate folders. This is because generally plugins only consist of two les: the XML manifest le and the root plugin le. Installed plugins are located in the root plugins folder in a subfolder named after the plugin group. Our example would be located in the folder plugins/foobar. In order to use your plugin, you will need to use the Plugin Manager to publish it. Events As we have already mentioned, plugins use the Observer pattern to keep an eye on events and handle them. The Observer pattern is a design pattern in a logical function, which is common to programming. This particular pattern allows listeners to attach to a subject. The subject can initiate a notication (essentially an event), which will cause the listeners to react to the event. The expressions 'listener' and 'observer' are interchangeable, as are 'subject' and 'observable'. If you are unfamiliar with the Observer pattern, you may want to refer to http://www.phppatterns.com/docs/design/observer_pattern. When we create plugins, we generally dene listeners for specic events. The application uses a global object called the event dispatcher to dispatch events to registered listeners. The global event dispatcher, a JEventDispatcher object, extends the abstract JObservable class. Chapter 6 [ 137 ] In Joomla! a listener can be a class or a function. When we use a class listener, the class should extend the abstract class JPlugin; we extend this class because it implements the methods that are used to attach the listener to a subject. This diagram illustrates the relationship between the JEventDispatcher class and listeners that extend the JPlugin class: There are several events that are used in the core. In addition to these, we can use our own events. We do not have to dene events; we can just use them. Let's imagine we have a component, which displays information about an entity called Foobar. We might choose to use a custom event called onPrepareFoobar to allow listeners to perform any additional processing to the Foobar data before we go ahead and display a Foobar. To issue an event, we trigger it. There is a method in the application called triggerEvent(), which triggers events in the global event dispatcher, notifying the relevant listeners. This is a pass-through method for the JEventDispatcher trigger() method. The triggerEvent() method accepts two parameters: the name of the event and an array of arguments to pass to the listener. Imagine we want to trigger the event onPrepareFoobar. This example shows how we can achieve this; it assumes $foobarData is an object that represents a Foobar entity. Note that $mainframe is the application. $arguments = array(&$foobarData); $result = $mainframe->triggerEvent('onPrepareFoobar', $arguments); Plugin Design [ 138 ] The most important thing to notice here is that we reference and wrap $foobarData in an array. The second parameter must always be an array. This array is dissected, and each element is used as a separate parameter when dispatching an event to a listener. We purposefully make sure that $foobarData is passed by reference so we can make changes to $foobarData in our listeners. Once all of the listeners have been updated, the method returns an array of responses. In our example this is recorded in $result. Imagine that all of the onPrepareFoobar listeners return a Boolean value. $result would contain an array of Boolean values. Listeners There is one more thing we need to do rst. We need to know how to attach listeners to the event dispatcher. Registering Listeners When we create a new plugin, if we are using functions, we must inform the application of each function and event. We do this using the application's registerEvent() method. The method accepts two parameters, the name of the event and the name of the handler. This acts as a pass-through method for the global event dispatcher register() method. Technically the name of the handler can be the name of a class. We rarely need to use the method in that context because when we load a plugin that denes a class, Joomla! automatically registers the class and events. For example, the core Joomla! search component uses plugins to search for results. The plugin that searches content articles uses the function plgSearchContent() to handle the onSearch event. This is how the function is registered: $mainframe->registerEvent('onSearch', 'plgSearchContent'); Handling Events We mentioned earlier that we could use functions or a class to handle events. We will start by exploring event handling using functions. Imagine we have a bespoke plugin called My Plugin in the group Foobar and we want to handle an event called onPrepareFoobar. Chapter 6 [ 139 ] Before we start building our function we need to name it; generally we use the following naming convention: the word plg, the plugin group, the element name, the event. For example, we might call the function plgFoobarMyPluginPrepareFoobar. This is an example of a function we could use to handle that event: $mainframe->registerEvent('onPrepareFoobar', 'plgFoobarMyPluginPrepareFoobar'); /** * Makes the name of the foobar uppercase. * * @param Foobar Reference to a Foobar object */ function plgFoobarMyPluginPrepareFoobar(&$foobar) { $foobar->name = strtoupper($foobar->name); } The most striking part of this function is the parameter. Earlier in this chapter, we described how to trigger an event and we passed an array; each element of that array is passed as a separate parameter to the listeners. In this example we can assume that the one parameter is the Foobar object, which we passed by reference in the triggering events example. A single plugin can contain multiple functions for handling multiple events. If we want to create a listener using a class, we extend the abstract class JPlugin. Before we start building a listener class, we must determine the name for the class. JPlugin subclasses follow a special naming convention: the word plg, the name of the plugin group, the name of the plugin element. For example, a plugin with the name myplugin in the group foobar might dene the JPlugin subclass plgFoobarMyplugin. This example is designed to handle two events: onPrepareFoobar and onAfterDisplayFoobar: // import the JPlugin class jimport('joomla.event.plugin'); /** * My Plugin event listener */ Plugin Design [ 140 ] class plgFoobarMyplugin extends JPlugin { /** * handle onPrepareFoobar event * * @param object Foobar to prepare */ function onPrepareFoobar(&$foobar) { $foobar->name = JString::strtoupper($foobar->name); } /** * handle onAfterDisplayFoobar event * * @param object Foobar which is being displayed * @return string XHTML to display after the Foobar */ function onAfterDisplayFoobar(&$foobar) { return '<p>'.JText::_('Foobar Name converted to upper case by My Plugin').'</p>'; } } The rst thing that should have struck you about this example is that we have not bothered to register any events with the global event dispatcher. The advantage of using classes is we do not need to do this, so long as we follow the strict class naming convention. If we do not follow the naming convention, we can register a class in the same way as we register a function, as described earlier in the chapter. When plugins are imported into Joomla! the global event dispatcher will automatically look for listener classes and register them. You probably also noticed the names of the two methods are identical to the names of the events they handle. This is essential when creating JPlugin subclasses. As we do not manually register each event to each method, this is the only way in which the event dispatcher can determine which event a method is designed to handle. The onAfterDisplayFoobar() method has one major difference to the other method; it returns a value. You may remember that earlier we mentioned that when an event is triggered we get an array of all the results. [...]... manifest file in detail: install (Root tag) The root tag, called install, identifies the type of extension and the version of Joomla! for which the extension is written Example Attributes type Type of extension version Version of Joomla! the extension is for Sub-tags author, authorEmail, authorUrl, copyright, creationDate, description,... Lieu of Library Extensions) We have mentioned the Joomla! library a number of times in the past Although the library is a powerful part of Joomla!, it is not extensible There are currently discussions within Joomla! to create library extensions and implement an extension dependency mechanism In the meantime, we can use plugins as libraries Plugins, although not designed for this, are ideally suited... editors that have already been ported for use with Joomla!: • ASBRU Web Content Editor • FCKeditor • wysiwygPro • XStandard Porting an editor for use with Joomla! is no easy task Intimate understanding of the editor and Joomla! editor plugins is required [ 146 ] Chapter 6 onDisplay Description Gets the XHTML field element to use as the form field element Parameters name Name of the editor area/form field... table describes the attributes that we are most likely to modify: Attribute Description created Created date and time in the format 0000-00-00 00:00:00 modified Modified date and time in the format 0000-00-00 00:00:00 text Body content of the item title Content Item Title toc Table of Contents [ 144 ] Chapter 6 onAfterDisplayContent Description Creates an XHTML string, which is displayed directly after... • editors • editors-xtd • search • system • user • xmlrpc [ 141 ] Plugin Design Each of these groups performs different functions, we will discuss precisely what they are and how they handle them in a moment In addition to the core groups, we can create plugins that belong to other groups For example, if we created a component named Foobar and we wanted to add plugins specifically for that component... Only has the keys 'id', which is the user's ID, and 'username', which is the user's username [ 1 54 ] Chapter 6 XML-RPC XML-RPC is a way in which systems can call procedures on remote systems via HTTP using XML to encode data Joomla! includes an XML-RPC server, which we can extend using plugins There are essentially two parts to XML-RPC plugins: the event handler for the event onGetWebServices, which returns... this does not apply; we never need to import 'system' plugins System plugins are imported irrespective of the request that is being handled It is, however, unlikely that we would ever need to trigger a system event because Joomla! should handle all system events So where and when do we import plugins? Well firstly, it does not matter if we attempt to import the same group of plugins more than once At... four different authentication methods: • GMail • Joomla! • LDAP • OpenID By creating new authentication plugins, we can allow Joomla! to support additional authentication methods It is common for businesses to run more than one system, each with its own authentication Joomla! authentication plugins allow us to integrate authentication between systems and reduce system management overheads There is only... the file according to a specific naming convention: the language tag, a period, the Joomla! parsed plugin name For example, the English translation file for the plugin My Extension would be called en-GB.plg_myextension.ini Plugin translation files are located in the administrator/language folders Unlike components and modules, plugin language files are not automatically loaded when a plugin is loaded... load it when a handler method or function is executed Dealing with Plugin Settings (Parameters) To deal with plugin settings we can use the, ever handy, params tag in our XML manifest file This example shows how we can add some simple parameters to a plugin: . ported for use with Joomla!: ASBRU Web Content Editor FCKeditor wysiwygPro XStandard Porting an editor for use with Joomla! is no easy task. Intimate understanding of the editor and Joomla! editor. Chapter 5 [ 13 1 ] Summary The two avors in which modules come, frontend and backend, essentially dene two different types of extension. Backend modules are often. called 'Foobar - My Extension& apos;. <?xml version=" ;1. 0" encoding="utf-8"?> <!DOCTYPE install SYSTEM "http://dev.joomla.org/xml /1. 5/ plugin-install.dtd"> <install

Ngày đăng: 14/08/2014, 11:21

Từ khóa liên quan

Mục lục

  • Mastering Joomla! 1.5 Extension and Framework Development

    • Chapter 5: Module Design

      • Summary

      • Chapter 6: Plugin Design

        • Setting Up a Sandbox

        • Events

        • Listeners

          • Registering Listeners

          • Handling Events

          • Plugin Groups

            • Authentication

            • Content

            • Editors

            • Editors-xtd

            • Search

            • System

            • User

            • XML-RPC

            • Loading Plugins

            • Using Plugins as Libraries (in Lieu of Library Extensions)

            • Translating Plugins

            • Dealing with Plugin Settings (Parameters)

            • Packaging

              • XML Manifest File

              • File Naming Conflicts

              • Summary

Tài liệu cùng người dùng

Tài liệu liên quan