News

Weld development mode and JMX support

2015-11-10   probe , jmx   Martin Kouba

Weld comes with a special mode for application development. When enabled, some interesting data are collected so that it’s possible to inspect and monitor application components at runtime. Data in JSON format are available through the REST API, eventually through the MXBean of name org.jboss.weld.probe:type=JsonData,context=ID where ID should be replaced with an identifier of an application. The JMX support might be especially useful for environments and applications which do not utilize a web container (Java SE, OSGi, etc.).

How to enable JMX support

Simply use the Weld configuration facility and org.jboss.weld.probe.jmxSupport configuration property. If set to true one or more MBean components may be registered so that it is possible to use JMX to access the Probe development tool data.

JMX client

So for example if using Weld SE without a web container it’s still possible to access the Probe data. There is a lot of JMX clients out there (for example jconsole or jvisualvm from the Oracle JDK). The problem is not all of us prefer reading JSON data. Hey wait! Weld Probe already has an HTML client, right? Yes, but this client works with REST API. We would have to embed a web container (e.g. Undertow) and add Weld Servlet or do some configuration manually. But what if there are multiple Weld instances in the same JVM? The configuration might become quite complex. Luckily, there is another solution - a working prototype of JMX client reusing the default HTML GUI.

Clone, build and run

    # Clone the git repo
        git clone git@github.com:weld/weld-probe-jmx.git
        # Specify the weld version used in your application and run the build
        mvn clean package -Dversion.weld=2.3.1.Final
        # Run the client
        java -jar target/weld-probe-jmx-1.0.0-SNAPSHOT-shaded.jar

How does it work?

  • First, the client attempts to connect to a JMX server (your application)

  • User may select a Weld container to inspect

  • Then the client starts an Undertow instance locally, HTML client is available at: http://127.0.0.1:8181/probe-jmx/weld-probe

  • Data are fetched remotely through JMX

  • User may reconnect at any time

See also the JBoss Forge example below to see an example output.

Configuration

Moreover, it’s also possible to configure the JMX server URL, Undertow host and port - used to expose the HTML client. E.g. for WildFly (standalone mode) a different jmxServiceUrl must be specified and jboss-client.jar must be also on the class path, e.g.:

java -Dorg.jboss.weld.probe.jmxServiceUrl="service:jmx:http-remoting-jmx://127.0.0.1:9990" -cp '/opt/jboss/wildfly/bin/client/jboss-client.jar:target/weld-probe-jmx-1.0.0-SNAPSHOT-shaded.jar' org.jboss.weld.probe.ProbeJmx

JBoss Forge example

An interesting use case would be to inspect JBoss Forge addons powered by CDI (works with Forge 2.20.1.Final and later). Before we start Forge we need to set some extra system properties:

export FORGE_OPTS="-Dorg.jboss.weld.development=true -Dorg.jboss.weld.probe.jmxSupport=true -Dorg.jboss.weld.probe.eventMonitor.containerLifecycleEvents=true -Dcom.sun.management.jmxremote.port=9999 -Dcom.sun.management.jmxremote.authenticate=false -Dcom.sun.management.jmxremote.ssl=false"

System properties starting with com.sun.management simply allow to connect to JMX remotely. org.jboss.weld.development enables the development mode. org.jboss.weld.probe.jmxSupport enables the JMX support. Finally, If org.jboss.weld.probe.eventMonitor.containerLifecycleEvents is set to true all the container lifecycle events are monitored during bootstrap.

Then start the Forge as usually and run the prototype. You should see a similar output:

Connecting to a remote JMX server: service:jmx:rmi:///jndi/rmi://127.0.0.1:9999/jmxrmi
    Select a Weld container (JSON data provider):
    [0] org.jboss.weld.probe:type=JsonData,context="org.jboss.forge.addon:shell_1447145001728"
    [1] org.jboss.weld.probe:type=JsonData,context="org.jboss.forge.addon:configuration_1447145001592"
    [2] org.jboss.weld.probe:type=JsonData,context="org.jboss.forge.addon:parser-java_1447145002037"
    [3] org.jboss.weld.probe:type=JsonData,context="org.jboss.forge.addon:bean-validation_1447145001526"
    [4] org.jboss.weld.probe:type=JsonData,context="org.jboss.forge.addon:javaee_1447145003135"
    [5] org.jboss.weld.probe:type=JsonData,context="org.jboss.forge.addon:ui_1447145001709"
    [6] org.jboss.weld.probe:type=JsonData,context="org.jboss.forge.addon:convert_1447145001526"
    
    [disconnected]$

Now select a Weld container to inspect, e.g. 5:

[disconnected]$ 5
    Connecting to the Weld container [5]: org.jboss.weld.probe:type=JsonData,context="org.jboss.forge.addon:ui_1447145001709"
    Starting Undertow...
    Lis 10, 2015 9:44:16 DOP. org.xnio.Xnio <clinit>
    INFO: XNIO version 3.3.1.Final
    Lis 10, 2015 9:44:16 DOP. org.xnio.nio.NioXnio <clinit>
    INFO: XNIO NIO Implementation Version 3.3.1.Final
    Weld Probe HTML client available at: http://127.0.0.1:8181/probe-jmx/weld-probe
    
    [connected #5]$

The HTML client is available at http://127.0.0.1:8181/probe-jmx/weld-probe. It’s also possible to reconnect or exit. Type help to get a list of all possible commands.


Weld 2.3.1.Final arrives...

2015-10-27   release   Martin Kouba

Weld 2.3.1.Final has been released! The delivery: a few killed bugs, couple of Weld SE enhancements and several Weld Probe improvements.

Notable bug-fixes and enhancements:

  • Private producer, disposer and observer methods should be intercepted (WELD-2043)

  • Specializing bean - remove @Default qualifier unless explicitly declared (WELD-2046)

  • Weld SE

    • Fix the development mode enablement

    • Allow to pass a ResourceLoader to be used for scanning (WELD-2044)

    • Allow to skip the registration of a shutdown hook (WELD-2051)

  • Weld Probe now supports monitoring of container lifecycle events during bootstrap (see also supported configuration properties)


Weld 2.3.0.Final released!

2015-9-18   release   Martin Kouba

Weld 2.3.0.Final has been just released! From now on, 2.3 is the current stable version of Weld and 2.2 is not actively developed anymore - i.e. no new features are added, only bugs will be fixed. Weld 2.3 will remain a CDI 1.2 implementation. We are incrementing the minor version due to several new features added. Weld 2.3 is also included in WildFly 10 application server.

Notable features and changes:

  • Java 6 support was dropped - Java 7 is the minimal requirement for building and running Weld 2.3

  • Weld 2.3 comes with a special mode for application development, the Probe development tool allows to inspect application CDI components at runtime

  • Weld SE Bootstrap API was enhanced in many ways - new features are mostly backported from Weld 3 development branch

  • Weld Servlet now supports Undertow web server

  • Revised delivery of @Initialized/@Destroyed events for @ApplicationScoped in an EAR (see also WELD-1821)

Weld 2.2.16.SP1

In addition, Weld 2.2.16.SP1 has been also released. It’s a bugfix release for 2.2 branch.


JDK 8u60 reveals a problem in Weld

2015-9-15   bug , jdk   Martin Kouba

Recently released JDK 8u60 has revealed a problem in Weld where not all synthetic members were ignored correctly. This has been fixed in 2.2.16.Final, 2.3.0.CR2 and 3.0.0.Alpha14 (not released yet). However, if not using a lambda referencing an event/disposed parameter inside an observer/disposer method, your application is most probably not affected. See also the related issue - WELD-2019.

Use case

If there is a lambda referencing an event/disposed parameter inside an observer/disposer method, the compiler creates a synthetic method with the event parameter as one of the method parameters. Since 8u60 the parameter annotations are preserved even for the synthetic method. And so Weld incorrectly recognizes these synthetic methods as observer/disposer methods.

Symptoms

You may get WELD-000409: Observer method for container lifecycle event can only…​ if using such a lambda in an extension or even WELD-001408 Unsatisfied dependencies for type…​ if using such a lambda in a regular observer and the lambda is using more references (i.e. not only event/disposed parameter) - these are also the method parameters of the synthetic method, and in CDI these additional parameters are injection points.

Example

class Foo {
      void observe(@Observes @Juicy String payload) {
        Arrays.asList("foo").stream().filter((s) -> s.equals(payload));
      }
    }

A synthetic method is created for the lambda and the event parameter is passed as a method parameter. The annotations are preserved. As a result Weld creates two observer methods having the same event parameter: @Observes @Juicy String payload.

Workaround

Instead of the event parameter reference use an additional local variable with the same value assigned:

public void observe(@Observes @Juicy String payload) {
       String p = payload;
       Arrays.asList("foo").stream().filter((s) -> s.equals(p));
    }

Weld team changes

2015-9-8   team   Jozef Hartinger

I am pleased to announce a couple of changes coming to the Weld team:

First of all, Martin will be taking over leadership of the project. Martin has proven himself to be an excellent engineer over all the years and I am happy that I can leave the project in his hands. His primary task is going to be leading the project towards the Weld 3 milestone.

Secondly, I will be moving to work temporarily on a different project. I truly enjoyed working on Weld and with the CDI community. Now after almost 4 years on the project I was given an exciting opportunity which I decided to pursuit.

Last but not least, Matěj Novotný is joining the team as a quality engineer. He’s going to work on expanding our testsuites and making sure Weld releases do not break anything :-)