Workshop Controls and Extensions: Part 1 - Writing an Extension

by Emmanuel Proulx and Lucian Agapie
01/31/2005

Abstract

WebLogic Workshop 8.1 offers a world of possibilities to those who know how to extend it. This article gives a real-world example of how to extend Workshop by adding a menu item, a toolbar button, and a frame. It is the first in a series examining Workshop controls and extensions. Future articles will look at the help system, wizards, distribution, and other topics.

Introduction

We're in an age of convergence. Convergence occurs when technologies merge. When BEA brought us WebLogic Workshop 8.1, it merged the best features of J2EE, web services, and the WebLogic Platform technologies. At the same time, BEA opened the door for merging custom technologies into Workshop. This is done using
controls and
extensions.

Workshop encompasses a highly customizable user interface, which includes the development environment, classes, runtime environment, and so on. In this series we will explore some of these features. We will do so by developing a set of controls and extensions called "plug-ins" by other IDE vendors. By the end of this series you should be able to quite comfortably build arbitrary extensions to the WebLogic Workshop environment.

Case Study

Before we start writing our controls and extensions, we need a case study. Sometimes we want to collaborate with remote developers. Let's assume that they don't have access to a source control repository. A good way to send them your source code is through email. But the process of opening your email client, attaching a Java file, and sending it can take a few minutes. What if you could send the document directly from inside Workshop?

In this article we are going to create a simple email client, which will be activated by a button or, alternatively, by a menu item.

By completing this project, you will learn how to:

create, manage, build, and deploy an extension project

create a menu item, a toolbar button, and a view in Workshop

invoke an extension programmatically

Extension Points

Extension points are a mechanism that determines the interface between the main Workshop program and extensions. It consists of a set of predefined places that allow the inclusion of arbitrary new objects, such as menus, toolbars, buttons, and views, on the main user interface.

The Workshop core comes with a set of extension points. Custom extensions can use these extension points to add their own features. These custom extensions can also add their own extension points for other extensions to use. This creates a hierarchy of extension points.

Extension points are retrieved by name (text value). They can hold objects that are of various types, depending on the kind of extension point. This means all extension points must be documented in order to be usable. A list of basic extension points is available in the Workshop help system. To view this list, go to the menu Help | Help Topics, then navigate to the category:

Contains the list of supporting libraries, which aren't in the classpath of Workshop but are needed for compilation and running

/controls_extensions/APP-INF/lib

Other folders aren't relevant for us. Notice that the last item isn't named like the folder it represents.

Figure 2 shows the resulting JAR file after the extension is compiled and archived.

Figure 2. Java archive structure

In the JAR file you will find the compiled files in their packages and other support files as they appear in the project.

Extending Workshop

The rest of this section provides a step-by-step guide to creating the email project. The complete source code is also available for download at the end of the article.

We will describe adding the extension by looking at several phases of development: creating the project structure, creating the build support files, creating the extension files, building the extension files, creating the support file, and, finally, implementing the extension.

Setting up our project

In this phase we will show you how to create a Workshop project for the extension and set up the classpaths and the integrated debugger.

1. First, we are going to create a new application. Select File | New | Application from the main menu. In the New Application dialog box choose an Empty Application from the All category. Type "dev2dev" in the Directory field and "controls_extensions" in the Name field. Leave the sample Workshop server, which appears as default in the Server field, and then click on the Create button.

A directory called
controls_extensions and subdirectories called
Modules,
Libraries, and
Security Roles will be created and will be visible in the Application pane. This is the application that will host our extension. A single application can contain many projects like extensions and controls.

2. Add a new project for the extension. Right-click on the folder named
controls_extensions in the Application pane, and then select File | New | Project. In the dialog box called New Project select the Java Project in the Business Logic category. Type "my_email" in the Project Name field, and press the Create button. A new folder called
my_email will appear in the Application pane under
controls_extensions.

This project represents a single extension. It will be built into a deployable extension JAR file.

3. Create a repository for the source files. Right-click
my_email, select New|Folder, type "src" in the Create New Folder dialog box, and then press OK. This is where all Java files will be saved under their respective packages. Only this folder will be compiled. Other folders contain supporting files.

4. Set the properties for the project. On the Application pane right-click on the project my_email, and select Properties from the menu. The project properties dialog box will appear. We will now set many things inside this dialog.

Note: The provided source code may not compile if these properties aren't set.

a) Select the Paths category.

Classpath: Workshop extensions need a special library in order to be compiled and executed. This is the
wlw-ide.jar library, and it contains all extension classes and interfaces. It is in the classpath when Workshop starts, but it is not in the classpath when compiling an extension. We need to add it. Click on the Add Jar button beside the Classpath list on the right side of the window, and browse to find:
BEA_HOME\weblogic81\workshop\wlw-ide.jar, where
BEA_HOME is the folder in which the BEA WebLogic is installed. This ensures the classes needed to build the application are provided.

Source path: We don't have to compile everything in our project. Only the
src folder contains Java code. We can specify this here. Click on Add Path beside the Source Path list on the right side of the window. Browse to find the
C:\bea\user_projects\applications\controls_extensions\src folder, and click Select Directory.

b) To compile our extension, we can rely on the default Workshop build mechanism. But this doesn't allow us to automatically deploy our extension. The only way we can do this is using an Ant build script. Workshop can create a default script that is customizable. Select Build on the left side of the window.

On the right side under Build Type click on "Export to ant file" under "Use IDE build," and then press the OK button in the dialog box. A new file,
exported_build.xml, has been created in the
my_email folder. We will customize this file later on.

c) Workshop is a great tool for extension development because it has an integrated debugger. But before we can debug an application we must configure Workshop. Select Debugger on the left side of the window.

On the right side of the window, under Debugging Options, check "Build before debugging," uncheck "Pause all threads after stepping," and then select the radio button for "Create new process." Type "workshop.core.Workshop" in the Main Class field and enable "Smart debugging." The extension is now ready for debugging. Simply set a breakpoint in the code, and then run the debugger. A new instance of Workshop will come up, and you will be able to step into the code of your extension!

For more information regarding debugging options, see Setting Up Extension Debugging Properties.

Creating the build support

In this phase we will show you how to customize our Ant build file.

5. Build file customizations: Since "exported_build.xml" isn't a common name or even the norm, let's rename it. In the Application pane right-click on the file
exported_build.xml under the
my_email project folder, and select Rename from the pop-up menu. Rename it to "build.xml" in order to be recognized by Ant.

Double-click on
build.xml to open it on the editor window. We are going to add the following lines at the end of the build task:

This command will copy the third-party mail.jar library to its deployment folder.

The last customization step is to make Workshop use our new Ant script instead of the default. Again, open the project properties, and in the Build category, click on the Use Ant Build radio button. Keep the defaults.

Creating extension.xml

At this point we have completed the preparation work. Let's dig into the coding part.

6. Workshop expects to find the controls and extensions deployment descriptors in a folder called
META-INF. Let's create it. Right-click on the
my_email project folder, and choose New | Folder from the pop-up menu. In the Dialog box type "META-INF," and press OK.

In this phase, we will show you how to create an extension point file and customize it to your needs. The mechanism for creating new extension points is beyond the scope of this article.

7. Add the file
extension.xml. This serves to define the extension objects as explained previously. Right-click on the
META-INF folder, and then choose New | Other File Types from the pop-up menu. In the New File dialog box that appears, choose "XML file" from the Common category, and name it "extension.xml." Then click the Create button. Be warned: If the file name or its contents have a typo, the extension will compile fine but will not work. There may not be any error message.

Let's write the contents of
extension.xml. This file starts with the root tag
<extension-definition>. Inside this there is a list of
<extension-xml> tags. Each tag describes a single kind of extension point. We want to create a toolbar button and a menu item. These extensions are both added in extension points of type "action." Therefore, the following is used to specify action extensions:

<extension-xml id="urn:com-bea-ide:actions">

The "id" attribute contains a unique identifier for the kind of extension point that interests us. The syntax for the inside of the
<extension-xml> tag is specified in the documentation. It is particular to each kind of extension point. For "actions," the syntax is two tags:
<action-ui> and
<action-set>. The first specifies the visible elements to create (menu, pop-up menu, toolbar button) and associates them to an action. The second lists those actions and the Java classes of type
IAction.

The relative positioning of menu items and toolbar buttons is specified by an integer "priority" attribute.

The path attribute serves to reference an already existing menu or toolbar. It contains a list of IDs of the parent menus/toolbars, separated by forward slashes ("/"). How do you know what IDs to use? Unfortunately, this isn't well-documented. We had to resort to looking inside the Shell extension (C
:\bea\weblogic81\workshop\extensions\shell.jar), in the file
extension.xml. This is where the basic menus and toolbars are created.

Keyboard shortcuts are represented by the "&" character (coded in XML it becomes "&amp;").

Images are loaded by the classloader. So they must be specified as a relative path to the root of the
src folder.

There are two UI elements (a toolbar button and a menu item), but there's only one action. Both UI elements execute the same action.

Creating the support files

In this phase we will show you how to create the support files for the project.

8. Create the file
MANIFEST.MF in the
META-INF folder. This tells Workshop where to look for any third-party libraries. In our case we need the JavaMail API library file. This is the content of
MANIFEST.MF:

Class-Path: ../lib/mail.jar

The destination folder for the extension JAR file is
C:\bea\weblogic81\workshop\extensions. So one level up and into the lib folder means the file mail.jar is located in the folder
C:\bea\weblogic81\workshop\lib.

9. The graphic files are to be put in the
images subfolder inside
src, as we just discussed. Graphics for toolbar buttons and menu items are 16x16 pixel GIF files, with transparent color set for the background. We created the file
email.gif, so you don't have to draw one yourself; just save this icon to your computer:

Implementing the extension

In a previous section we defined the class to be executed for an action in the
class attribute of the
<action> element. Now we will implementing this class.

10. Let's code the action class. Create the file:
/dev2dev/controls_extensions/EmailApplication.java. This class must implement the
IAction interface. A convenient way to do this is to subclass the
DefaultAction. This way only the
actionPerformed() method has to be implemented. This method is called by Workshop when the action is executed. In our case this method opens a new frame to enter the email information. We will create this frame later. For now just type in the following listing:

This piece of code is an example of how one can programmatically instantiate an extension. One could also display this same pane by adding a frame extension in
extension.xml.

Workshop contains many classes that allow manipulating its windowing system and internal state. The
FrameSvc is a helper class to create new panes in the Workshop GUI. Here we summon the
EmailFrame class by name, and we specify its placement using a
LayoutConstraints object. Refer to Workshop's documentation for help with these classes. This is available in the menu Help | Help topics, then in the category WebLogic Workshop Reference, Workshop API Javadoc Reference, Extension API Reference. You will have hours of fun browsing the many classes here.

In short, we have here a
JPanel that contains a To field (destination address), a Subject field, and a Send button. Inside the Send button, we use the
JavaMail API to send an email with the document opened in the editor.

Three interesting classes are used here. One is
Application, which is used to retrieve the active (opened) document. The second is
IDocument, an interface that represents that document. This has a
getURI() method that returns the location of the file. Finally, there's the very cool
IOUtil, used here to copy the file into a
String. These are all documented in the
Extension API Reference as noted above.

The Result

After the project has been built, select Debug | Start from the main menu. Note the email icon on the left side of the toolbar as well as the new item named Email in the main menu. If you click on the icon a new frame is going to appear along the top side with the To and Subject fields and the Send button, as you can see in Figure 3.

Figure 3. Result of the project

Conclusion

With Workshop's powerful, easy-to-use extension mechanism, convergence is achievable. Whatever technology you use in your company, you can now easily integrate it into Workshop as an extension or a control. As you can see, there are many more tools to investigate in Workshop, so there are countless applications one can develop.

In the next article we will explore the Workshop help system, and we will supplement a control with documentation suitable for official validation (validated controls and extensions can be added to the Premier Component Gallery).

Emmanuel Proulx is an expert in J2EE and SIP. He is a certified WebLogic Server engineer.

Lucian Agapie is a senior electrical engineer, member of IEEE, who enjoys writing software applications in Java, C++ and TCL/TK.