Making your Application monitorable in GlassFish v3

Monitoring in GlassFish v3 - Blog

1. Introduction
2. Writing Probes in your App
3. Writing a StatsProvider for your App
4. Registering the StatsProvider
5. Making your App an OSGI bundle
6. Deploying your OSGI App
7. Viewing the monitoring data for your App
8. Scripting Client\*
9. Running the scripting client
10. Architecture
11. Conclusion
12. References

\*- The features denoted with '\*' are the value-add features available only for the paid customers.


1. Introduction

Monitoring in GlassFish v3 is new and it comes with a lot of capabilities that will help the user to seamlessly use the canned container monitoring, as well as make their own components and user apps monitorable.

Salient features of Monitoring Infrastructure are
  • Monitoring is very Easy to Use.
  • It is Lightweight, events are emitted only when there are listeners
  • Container(s) / sub-system only emit events/probes
    • Example: onWebRequest(...), onWebResponse(...)
    • Interesting values are passed as paramters
    • Containers do NOT maintain any stats
    • We use the term "providers"
    • If there are no listeners registered for this, then there is no overhead
  • Listeners receive the event that are emitted by providers
    • Listeners can examine the parameters passed
    • Listeners maintain the stats
  • The Monitoring framework connects “providers” and “listeners”
  • Supports various clients, like asadmin, JMX/AMX, REST, Admin GUI
  • Monitoring events are exposed as probes in the DTrace\* world
  • Adhoc monitoring capability using DTrace\* and Scripting-Client\* (JavaScript)
  • Extensible and Pluggable, allowing you to make your modules and user apps monitorable
  • Allows monitoring at a very granular level (Collect stats based on Probes rather than at container level)
  • Allows the Turning on/off, (configuring) the monitoring for glassfish as well as their own components and applications
\*- Available as a value-add feature, made available only to the paid customers.

This blog will talk about making a user App monitorable by using the Pluggable and Lightweight Monitoring Infrastructure, and how it will expose your probes and statistics to various clients. I have enhanced Byron's sample to demonstrate this feature.

The WebApp we are going to use consists of a Servlet (which is also a ProbeProvider), StatsProvider (MyProbeListener) and a pom.xml. You can either download the war or the sources from this zip.

2. Writing Probes in your App

Probe points are the monitoring events, emitted when glassfish goes through that code path. The Probes are defined as part of ProbeProvider definition. The Providers and its probes are discovered and registered automatically by the Monitoring infrastructure and thus exposed to the DTrace, Client-Scripting and Probe Listener clients.

Following is the code snippet on how to write a probe in your web application. Note that the only dependency that your App will have is on management-api.jar which is an externalized maven module. There is no dependency on GlassFish itself, thus making your App portable.

ProbeProvider as a class

import org.glassfish.external.probe.provider.annotations.\*;
import org.glassfish.external.probe.provider.StatsProviderManager;
import org.glassfish.external.probe.provider.PluginPoint;

@ProbeProvider (moduleProviderName="glassfish", moduleName="samples", probeProviderName="ProbeServlet")

public class ProbeServlet extends HttpServlet {

   @Probe(name="myProbe")
    public void myProbe(
           @ProbeParam("probeArg") String s) {
        if (StatsProviderManager.hasListeners("glassfish:samples:ProbeServlet:myProbe"))
            System.out.println("Firing the probe (listener(s) exist): " + s);
        else
            System.out.println("Listeners Doesn't exist, the probe will not be fired: " + s);
    }

    protected void doGet(HttpServletRequest request, HttpServletResponse response)
    throws ServletException, IOException {
        myProbe("Hello #" + counter.incrementAndGet());

When you write your ProbeProvider as an XML, you will not even have a dependency on management-api.jar.
ProbeProvider as an xml

<probe-provider moduleProviderName="glassfish" moduleName="samples" probeProviderName="ProbeServlet" >
    <probe name="myProbe"                                                        
       <class>com.sun.samples.ProbeApp.ProbeServlet</class>
       <method>myProbe</method>
       <signature>void (String)</signature>
       <probe-param type="String" name="probeArg"/>
       <return-param type="void" />
    </probe>
</probe-provider>

3. Writing a StatsProvider for your App


A Probe listener (part of the functionality of StatsProvider Object) is basically an object that receives callbacks from the providers. A method in the listener can be "marked" as callback method for a particular event from a specific provider.

StatsProvider are the objects which gather and expose the monitoring data of various components. They do the following functionality
  • Allows configuration of a component for Monitoring i.e, Enable/Disable
  • Gathers statistics
    • Defines the Statistics Objects
    • May Listen (Via. Probe Listeners) to Probe events emitted by Provider
    • May collect statistics based on the probe events or however way it wants (for ex. using some specific container events)
    • Also may collect statistics from non-Probe Provider, Ex. JVM statistics
  • The statistics objects will be publised to the Monitoring Registry
  • They are the target objects for asadmin, AMX/JMX and REST clients
Following is the snippet of the StatsProvider for our web application

@ManagedObject
public class MyProbeListener {
    private CountStatisticImpl requestCount;

    public MyProbeListener() {
        requestCount = new CountStatisticImpl(
            "RequestCount", StatisticImpl.UNIT_COUNT,
            "Request count");

    }

    @ManagedAttribute(id="requestCount")
    public CountStatistic getRequestCount() {
        return requestCount;
    }

    @ProbeListener("glassfish:samples:ProbeServlet:myProbe")
    public void probeListener(
            @ProbeParam("probeArg") String s) {
        requestCount.increment();
        System.out.println("PROBE LISTENER HERE.  Called with this arg: " + s);
    }

In the above sample, we are exposing the Statistic 'requestcount' by annotating the getter with @ManagedAttribute. We have designated 'probeListener' method as callback for the probe, by annotating that method with @ProbeListener. We are also using the Statistic classes which are part of the management-api.jar

4. Registering the StatsProvider

Once you write the StatsProvider, you will need to register it with the Monitoring infrastructure. Following code snippet shows how to do this.

Registering a StatsProvider Object

    public void init() throws ServletException {
        try {
            StatsProviderManager.register("web-container", PluginPoint.APPLICATIONS, "myapp",
                                                               new MyProbeListener());

        }
        catch(Exception e) {
            throw new ServletException("Error initializing", e);
        }

In the above example the StatsProvider object will be registered under the “server/applications” node (second parameter PluginPoint.APPLICATIONS) in the Monitoring registry. First parameter, tells us to tie all the Statistics objects for the given ProbeListener to the config element 'web-container'. Using this config element you can turn the monitoring to ON/OFF (with asadmin set command). You can as well choose to create your own monitoring config element for your component (see Sreeni's blog) and pass it here. Third parameter gives the intermediary sub-tree (followed after the 'server/applications' node) in the Monitoring registry under which the Statistics objects (defined in the StatsProvider object) would be created as leaf nodes. The fourth parameter is the StatsProvider object itself.

>asadmin get server.applications.myapp..\*   //will return these stats objects

5. Making your App an OSGI bundle

The monitoring infrastructure will discover the probe providers whenever an OSGI module is loaded,. This is done by the infrastructure by looking at the manifest entry 'Probe-Provider-Class-Names' (or Probe-Provider-XML-File-Names). You can make your App an OSGI bundle as follows. Note that you dont have any compile time or runtime dependency on glassfish when writing the probes or statsProvider. The only dependency you have is on Gmbal and management-api modules (none if you are using xml approach), which are externally hosted on maven.

Making your App an OSGI bundle
...
    <plugin>
        <artifactId>maven-war-plugin</artifactId>
        <version>2.1-alpha-2</version>
        <configuration>
            <archive>
                <manifestFile>${project.build.outputDirectory}/META-INF/MANIFEST.MF</manifestFile>
                <manifestEntries>
                    <Bundle-ClassPath>WEB-INF/classes/</Bundle-ClassPath>
                </manifestEntries>
            </archive>
        </configuration>
    </plugin>
    <plugin>
        <groupId>org.apache.felix</groupId>
        <artifactId>maven-bundle-plugin</artifactId>
        <version>2.0.0</version>
        <configuration>
            <supportedProjectTypes>
                <supportedProjectType>jar</supportedProjectType>
                <supportedProjectType>bundle</supportedProjectType>
                <supportedProjectType>war</supportedProjectType>
            </supportedProjectTypes>
            <instructions>
              <Probe-Provider-Class-Names>com.sun.samples.ProbeApp.ProbeServlet</Probe-Provider-Class-Names>
              <DynamicImport-Package>org.glassfish.flashlight.provider</DynamicImport-Package>
              <Web-ContextPath>/prober</Web-ContextPath>
                <Private-Package>com.sun.samples.ProbeApp.ProbeServlet</Private-Package>
            </instructions>

Following is what you see in the Manifest file of your app.

Manifest file

6. Deploying your OSGI App 

You will not do a regular deploy of web App which is now an OSGI bundle. Instead you would copy this to $INSTALL/domains/domain1/autodeploy/bundles directory.
Once you do this, you would immediately see that the App Server is automatically loading this bundle, in the process your Probe Provider in the App is processed and you should start seeing your probes as part of the 'asadmin list-probes' command.

copy app to autodeploy/bundles

Once you do this, you would immediately see that the App Server is automatically loading this bundle.
Following is the screenshot of the server.log, showing the loading of your OSGI'sed App.

autodeploy of OSGI app


As the OSGI bundle (app) is loaded automatically, the monitoring infrastructure will discover the Probe Provider in that bundle and will process it. As a result you should start seeing your probes as part of the 'asadmin list-probes' command. These probes will also be visible in the DTrace world (on supported platforms).

list-probes

7. Viewing the monitoring data for your App

By just using the StatsProviderManager API to register your StatsProvider, Monitoring Infrastructure will magically expose your data to various clients. This is demonstrated in this section.

i. asadmin client

Following screenshot show how to view the statistics that you are exposing from your app.
  1. To start with the monitoring is turned off by default. So, any attempt to view them will result in no stats.
  2. Since you tied your statistics object to the 'web-container' configuration, you will need to turn the monitoring for 'web-container' to ON.
  3. When you try to do 'asadmin get -m "\*"|grep myapp', this will show the statistics that are exposed by your app.
  4. Try accessing the App 'curl http://localhost:8080/prober/" and you will see your stats getting incremented.
Viewing stats

ii. RESTful client

You can use REST client to view the same stats by accessing the URL 'http://localhost:4848/monitoring/domain/server/applications/myapp' from your browser. Following is a snapshot of what you will see.

Restful Client

iii. JMX client

You can use REST client to view the same stats by accessing the URL 'http://localhost:4848/monitoring/domain/server/applications/myapp' from your browser. Following is a snapshot of what you will see.

JMX Client

iv. Admin GUI

You can use Admin GUI's pluggability API, to customize and display the monitoring for your app. See the blogs from Admin GUI team on how to do this.

v. DTrace

This is a Value-add feature and available only to the paying customers. All the probes that you wrote in the App will be exposed to the DTrace world on supported platforms. You can write the d-script to listen to these probes and collect your own statistcis as you get the callback from the probes in your app. Please refer to the documentation of DTrace on how to do this. More on this here.

8. Scripting Client\*

This is a Value-add feature and available only to the paying customers. We expose all our probes to a scripting client that would allow GF user to enable/disable the probes and get the data they want. This is similar to DTrace philosophy but will work on any OS for GlassFish runtime. Monitoring infrastructure exposes a Scripting Container and the asadmin client for deploying and running the scripts written in JavaScript and JRuby (next release) and opening up a Comet channel to display the data as and when the probe is fired (a Push model, does it asynchronously). Note that the script is something similar to a StatsProvider object in this case, the difference being, the user could write adhoc script (no compilation is necessary) and just run it on the fly to see the data instantly.

Lets see how we do this for the probe exposed by our app. Following is the javascript which will act as a listener for our probe and will collect the statistics (number of requests) and display the data on to the console whenever a callback from the probe is received.

Javascript example (appRequest.js)

var nRequests=0;

function requestReceived(probeArg) {
    nRequests = nRequests + 1;
    client.print( '\\n js> Request received event called, ' +
            ' arg= ' + probeArg +
            ' and count = ' + nRequests);
}

params = java.lang.reflect.Array.newInstance(java.lang.String, 1);
params[0]="probeArg";

scriptContainer.registerListener('glassfish:samples:ProbeServlet:myProbe', params, 'requestReceived');

9. Running the scripting client

Following are the steps used to demonstrate the scripting-client capability
  1. Invoke the servlet of your App 'curl "http://localhost:8080/prober/" '
  2. tail the last two lines in the server.log. Since there are no listeners (web-container is turned off by default), you will see that the probe is not fired. The probes will be fired only when there are listeners. This is how the Monitoring infrastructure makes the monitoring lightweight.
  3. Now run the scripting-client using the command 'asadmin run-script ~/samples/appRequest.js'. The command will wait for your javascript to print something (using client.print) so it can display on the asadmin console. Since the client.print in your script is done as part of the callback from probe, you will need to make the probe to fire.
  4. Access your App from the browser with the URL 'http://localhost:8080/prober/'. Do this a couple of times.
  5. On the console where you are running the 'asadmin run-script', you will start seeing the output which is the result of client.print from callback function in your script.
  6. Stop the scripting-client, do \^C. This will stop the scripting-client and as a result will remove the listener for your probe.
  7. Access the App to see if the probe is still firing - do 'curl "http://localhost:8080/prober/" '
  8. Doing a 'tal -2 server.log' will show you that there are no listeners for this probe and thus the probe is not fired
Scripting-client

10. Architecture

To get a bigger picture of overall v3 monitoring, look at the following architecture diagram.

architecture

11. Conclusion

We just saw how powerful is the Monitoring in GlassFish V3. Monitoring is lightweight, more granular, easy to use, pluggable, extensible, and comes with multi-client support. Monitoring is also possible by writing Adhoc scripts using the DTrace and Scripting-client features. Its very evident that Monitoring in V3 will be a great value-add for GlassFish users and is a clear differentiator as far as the competition is concerned.

12. References

Monitoring in GlassFish v3
Byron's blog - Monitoring in WebApp
Making Module Monitorable
Guidelines for writing ProbeProviders and StatsProviders
Writing Probes - Presentation
Monitoring Functional Specification


Comments:

<h5><i>[url=http://www.bagcheap.com]mens suits cheap[/url]</i></h5>
<h2><i>[url=http://www.watches-replicas.net]swiss army watch men[/url]</i></h2>
<h2><i>[url=http://www.bagcheap.com/replica-Chanel-handbags-2009-4-b0.html]cheap chanel handbags[/url]</i></h2>
<h2><b>[url=http://www.watches-replicas.net]watches replica[/url]</b></h2>
<h2><i><b>[url=http://www.replica-jewelry.net]ring jewellery[/url]</b></i></h2>
<i><b>[url=http://www.bagcheap.com]t shirts cheap[/url]</b></i>
<h2><i><b>[url=http://www.handbags-women.com]travel bags women[/url]</b></i></h2>

Posted by asd on March 02, 2010 at 06:20 PM PST #

Post a Comment:
  • HTML Syntax: NOT allowed
About

bloggerprashanth

Search

Categories
Archives
« April 2014
SunMonTueWedThuFriSat
  
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
   
       
Today