So far we have seen how to customize the output within the terminal, how to display messages in popups or execute custom JavaScript. In this section we will look at the so-called ClientExtensionService that can be accessed via the GLOBALS object. The ClientExtensionService offers methods to insert entries to various toolbars and context menus. Each new entry comes with a callback, that is, a ReportServer script that is executed when the specified entry is activated. Depending on where you added the entry your script is provided with additional information. For example, when adding an entry to the context menu in the report management view in the admin module, your script will get the id of the corresponding report object as an argument.
One thing to keep in mind when using the ClientExtensionService is that all effects are only valid as long as the current page is not refreshed. In order to install the changes permanently you should thus add the script into the onlogin.d folder.
The ClientExtensionService currently offers the following methods.
addStatusBarLabel() | Allows to display info texts in the status bar. |
addMenuEntry() | Allows to add entries to certain context menus. |
addToolbarEntry() | Allows to add buttons to certain toolbars. |
addReportExportOutputFormat() | Allows to create custom exporters. We discuss this in detail in Chapter 12. |
The first method (addStatusBarLabel) allows you to add simple info texts to the status bar. The concept is best explained by a small example.
def service = GLOBALS.services['clientExtensionService']
service.addStatusBarLabel("All is fine")
As you might have guessed, the first line obtains the ClientExtensionService from the GLOBALs object. All that is left to do is to set a status update. Besides just adding text you can also call
addStatusBarLabel("All is fine", "path to some icon", true)
where the second parameter should point to an icon and the third parameter controls whether the object is added to the left or to the right (default).
You can of course access all server objects and methods within this script. E.g., the following executes a given dynamic list and prints the report name and its number of records into the status bar.
import net.datenwerke.rs.base.service.reportengines.table.entities.*
import net.datenwerke.rs.base.service.reportengines.table.*
import net.datenwerke.rs.core.service.reportmanager.*
import net.datenwerke.rs.base.service.reportengines.table.entities.TableReportVariant
import net.datenwerke.rs.core.service.reportmanager.ReportService
import net.datenwerke.rs.core.service.reportmanager.ReportExecutorService
import net.datenwerke.rs.base.service.reportengines.table.output.object.RSTableModel
import net.datenwerke.rs.core.service.reportmanager.engine.config.ReportExecutionConfig
ReportService reportService = GLOBALS.getRsService(ReportService.class)
ReportExecutorService reportExec = GLOBALS.getRsService(ReportExecutorService.class)
TableReportVariant report = reportService.getReportById(2078898)
String reportName = report.getName()
RSTableModel reportCompiled = (RSTableModel) reportExec.execute(report, "RS_TABLE", ReportExecutionConfig.EMPTY_CONFIG)
int rowCount = reportCompiled.getRowCount()
/* prepare output */
def ces = GLOBALS.services.clientExtensionService
ces.addStatusBarLabel("Info: ${reportName} - ${rowCount} rows")
The ClientExtensionService allows you to add menu entries to the following context menus
Module | Description | Menu Name |
Datasource Manager | The datasource manager within the admin module | datasource:admin:tree:menu |
Report Manager | The report manager within the admin module | reportmanager:admin:tree:menu |
File Server | The file server within the admin module | fileserver:admin:tree:menu |
Dashboard Library | The dashboard library within the admin module | dashboard:admin:tree:menu |
User Manager | The user manager within the admin module | usermanager:admin:tree:menu |
To add an entry to a specific menu you need to access the menu by name (we give the menu names in the above table, for example, usermanager:admin:tree:menu corresponds to the context menu within the user manager tree).
The simplest way to add a menu entry is to simply call the method addMenuEntry() from the ClientExtensionService:
public void addMenuEntry(String menuName, String entryName, String scriptLocation, String configArgument)
The method takes the menu name, a name for the entry, a location of the script that is to be called when the entry is activated, and an argument given to the script. In the following we want to add a menu to the user tree. We call our script that generates the entry adddisplayinfoentry.groovy.
def service = GLOBALS.services['clientExtensionService']
service.addMenuEntry("usermanager:admin:tree:menu", "display info", "fileserver/bin/extensions/menu/displayuserinfo.groovy", "an argument")
If you execute the above script and navigate to the user manager in the administration module and right click on any item in the tree you will see the new entry.
display info
If you activate the entry you will see an error message, since we haven't yet created a script at location
fileserver/bin/extensions/menu/displayuserinfo.groovy
We are now going to create this file and use the above and display a simple message outputting the object's id.
import net.datenwerke.rs.terminal.service.terminal.obj.*
def result = new CommandResult()
def msg = new CreMessage("ID: " + context['id'] + ", args" + args)
result.addExtension(msg)
return result
The important part here is the context object which contains a field id corresponding to the id of the object clicked upon. Besides the id, the context also contains
id | The object's id. |
classname | The object's classname. |
path | The object's path. |
Sometimes it might be inconvenient to add the menu entry to every object in the tree. That is, maybe we want to add an entry only to user objects, but not to groups or organizational units. To have full control over how the menu item is created you can directly create an object of type AddMenuEntryExtension located in package net.datenwerke.rs.scripting.service.scripting.extensions. To better control when the entry is displayed, use DisplayConditions (located in the same package).
import net.datenwerke.rs.scripting.service.scripting.extensions.*
def service = GLOBALS.services['clientExtensionService']
def entry = new AddMenuEntryExtension()
entry.setMenuName("usermanager:admin:tree:menu")
entry.setLabel("display info")
entry.setScriptLocation("fileserver/bin/extensions/menu/displayuserinfo.groovy")
def cond = new DisplayCondition("classname", "net.datenwerke.security.client.usermanager.dto.UserDto")
entry.addDisplayCondition(cond)
service.addMenuEntry(entry)
Besides adding entries to context menus, you can add buttons to various toolbars, including all toolbars within the various admin modules. The mechanism is similar to the mechanism we described above. The following toolbars support the addition of custom buttons:
Module | Description | Menu Name |
Datasource Manager | The datasource manager within the admin module | datasource:admin:view:toolbar |
Report Manager | The report manager within the admin module | reportmanager:admin:view:toolbar |
File Server | The file server within the admin module | fileserver:admin:view:toolbar |
Dashboard Library | The dashboard library within the admin module | dashboard:admin:view:toolbar |
User Manager | The user manager within the admin module | usermanager:admin:view:toolbar |
Report Executor | The report executor module. This includes the report execution by URL. | reportexecutor:main:toolbar |
Scheduler Job List | The scheduler job list module. | schedulerlist:main:toolbar |
Similar as above you can either use helper methods within the ClientExtensionService such as
public void addToolbarEntry(String toolbarName, String entryName, String entryIcon, String scriptLocation, String arguments){
or alternatively create an object of type AddToolbarEntryExtension, also located in the package net.datenwerke.rs.scripting.service.scripting.extensions.
import net.datenwerke.rs.scripting.service.scripting.extensions.*
def service = GLOBALS.services['clientExtensionService']
def entry = new AddToolbarEntryExtension()
entry.setToolbarName("usermanager:admin:view:toolbar")
entry.setLabel("display info")
entry.setIcon("path/to/icon")
entry.setScriptLocation("fileserver/bin/extensions/menu/displayuserinfo.groovy")
def cond = new DisplayCondition("classname", "net.datenwerke.security.client.usermanager.dto.decorator.UserDtoDec")
entry.addDisplayCondition(cond)
service.addToolbarEntry(entry)
The possibilities offered by the ClientExtensionService are still rudimentary. We plan to extend these in future versions and are keen to hear your thoughts on what you would like to be able to do and what you are currently missing.