• Stars
    star
    31
  • Rank 820,005 (Top 17 %)
  • Language
    Scala
  • License
    Apache License 2.0
  • Created over 10 years ago
  • Updated over 4 years ago

Reviews

There are no reviews yet. Be the first to send feedback to the community and the maintainers!

Repository Details

scala JMX API

JAJMX - High level scala JMX API Build Status License Maven Scaladex Codacy codecov

The goal is to simplify jmx operations on remote (or local) JVM. Work on this library is still in progress... but implemented features work well. One of the main usages of this jmx abstraction layer is to simplify extraction of jmx metrics such as getting jdbc connections or busy threads usage trends. This library only requires one IP and one PORT in order to connect to a remote JMX plateform, no service url is required !

Scala docs

In your build.sbt, add this (available in maven central) :

libraryDependencies += "fr.janalyse"   %% "janalyse-jmx" % version

Console mode usage example :

 $ java -jar jajmx.jar 
Welcome to Scala version 2.10.1 (Java HotSpot(TM) 64-Bit Server VM, Java 1.6.0_45).
Type in expressions to have them evaluated.
Type :help for more information.

scala> import jajmx._
import jajmx._

scala> val jmx = JMX()

scala> import jmx._
import jmx._

scala> verbosegc()

scala> gcforce()
[GC 62584K->30221K(310080K), 0.0015270 secs]
[Full GC 30221K->30014K(310080K), 0.1879440 secs]

scala> osVersion
res3: Option[String] = Some(3.7.10-gentoo)

scala> osName
res4: Option[String] = Some(Linux)

scala> mbeans.take(10).map(_.name).foreach{println _}
java.lang:type=Memory
java.lang:type=MemoryPool,name=PS Eden Space
java.lang:type=MemoryPool,name=PS Survivor Space
java.lang:type=MemoryPool,name=Code Cache
java.lang:type=GarbageCollector,name=PS MarkSweep
java.lang:type=Runtime
java.lang:type=ClassLoading
java.lang:type=Threading
java.util.logging:type=Logging
java.lang:type=Compilation

scala> val mythreading=get("java.lang:type=Runtime")
mythreading: Option[fr.janalyse.jmx.RichMBean] = Some(RichMBean(java.lang:type=Runtime,<function0>,<function1>,<function2>,<function2>))

scala> mythreading.map{_.attributes.foreach{attr => println(attr.name)}}
SynchronizerUsageSupported
ThreadCount
TotalStartedThreadCount
ThreadAllocatedMemorySupported
ThreadContentionMonitoringSupported
ThreadAllocatedMemoryEnabled
AllThreadIds
DaemonThreadCount
ThreadContentionMonitoringEnabled
CurrentThreadUserTime
PeakThreadCount
ObjectMonitorUsageSupported
ThreadCpuTimeSupported
CurrentThreadCpuTime
ThreadCpuTimeEnabled
CurrentThreadCpuTimeSupported

scala> close

scala> :q

gcforce script

Only provide to the script, host and port of a remote JVM with JMX enabled, and this script will force the JVM to Garbage Collect major operation.

#!/bin/sh
exec java -verbosegc -jar jajmx.jar "$0" "$@"
!#

if (args.size < 2) {
  println("Usage   : jmxgrep host port")
  println("  args are not compliant so now let's connecting to myself, and force a gc...") 
}

import fr.janalyse.jmx._

val options = args.toList match {
  case host::port::_ => Some(JMXOptions(host,port.toInt))
  case _ => None
}
JMX.once(options) { _.gcforce }

A short gc force script (a self test) :

#!/bin/sh
exec java -jar jajmx.jar "$0" "$@"
!#

jajmx.JMX.once() { jmx =>
  jmx.verbosegc() 
  jmx.gcforce()
}

lsnum script

This scala script search for jmx numerical values. This jmxgrep script can be tested against itself : "lsnum"

#!/bin/sh
exec java -jar jajmx.jar "$0" "$@"
!#

import fr.janalyse.jmx._

val options = args.toList match {
  case host::port::_ => Some(JMXOptions(host,port.toInt))
  case _ => None
}

JMX.once(options) { jmx =>
  for {
    mbean <- jmx.mbeans
    attr  <- mbean.attributes.collect{case n:RichNumberAttribute => n}
    value <- mbean.getLong(attr)
    } {
    println(s"${mbean.name} - ${attr.name} = ${value}")
  }
}

jmxgrep script

This scala script search matching mbean name, attribute name, or value satisfying the given set of regular exception. This jmxgrep script can be tested against itself : "jmxgrep - vendor version"

#!/bin/sh
exec java -jar jajmx.jar "$0" "$@"
!#

import jajmx._

if (args.size == 0) {
  println("Usage   : jmxgrep host port - searchMask1 ... searchMaskN")
  println("  if no args given so now let's connecting to myself, and list my mbeans...") 
}

val (options, masks) = args.toList match {
  case host::port::"-"::masks => 
            (Some(JMXOptions(host,port.toInt)), masks.map{s=>("(?i)"+s).r})
  case "-"::masks => (None, masks.map{s=>("(?i)"+s).r})
  case _ => (None,List.empty[util.matching.Regex])
}

def truncate(str:String, n:Int=60) = {
  val nonl=str.replaceAll("\n", " ").replaceAll("\r", "")
  if (nonl.size>n) nonl.take(n)+"..." else nonl
}

JMX.once(options) { jmx =>
  for {
     mbean <- jmx.mbeans
     attr  <- mbean.attributes
     value <- mbean.getString(attr) } {
     
    val found = List(mbean.name, attr.name, value).exists{item =>
       masks.exists{_.findFirstIn(item).isDefined }
    }
    if (masks.isEmpty || found) 
      println(s"${mbean.name} - ${attr.name} = ${truncate(value)}")
  }
}

lsthreads script

Connect to a remote JVM using just the host adress and the used JMX port, and then list all active threads and their current states.

#!/bin/sh
exec java -jar jajmx.jar "$0" "$@"
!#
import jajmx._

val options = args.toList match {
  case host::port::_ => Some(JMXOptions(host,port.toInt))
  case _ => None
}

JMX.once(options) { jmx =>
  for (dump <- jmx.threadsDump(0)) {
    val threads = dump.threads
    val countByState = 
        threads
          .groupBy(_.status)
          .map{ case (state,sublist) => state -> sublist.size}
          .map{ case (state,count) => state+":"+count}
          .mkString(" ")
    
    println("Total %d threads,  %s".format(threads.size, countByState))
    for ( ti <- threads sortBy {_.id } ) {
      println("%d - %s - %s".format(ti.id, ti.status, ti.name) )
    }
  }
}

JMX Configuration Notes

Default JSR160 Configuration

JAVA_OPTS=$JAVA_OPTS" -Dcom.sun.management.jmxremote"
JAVA_OPTS=$JAVA_OPTS" -Dcom.sun.management.jmxremote.port=2500"
JAVA_OPTS=$JAVA_OPTS" -Dcom.sun.management.jmxremote.authenticate=false"
JAVA_OPTS=$JAVA_OPTS" -Dcom.sun.management.jmxremote.ssl=false"
JAVA_OPTS=$JAVA_OPTS" -Djava.rmi.server.hostname=192.168.0.184"

With authentication :

JAVA_OPTS="$JAVA_OPTS -Dcom.sun.management.jmxremote.authenticate=true"

$JAVA_HOME/jre/lib/management/jmxremote.password
$JAVA_HOME/jre/lib/management/jmxremote.access

FOR JBOSS 5.1

STANDARD JMX can be used to get JBOSS metrics, but unfortunately JVM metrics can't be gotten (Interesting information : http://labs.consol.de/blog/jmx4perl/jboss-remote-jmx/)

  • ENABLE standard JMX (-Dcom.sun.management.jmxremote*) AND USE A DIFFENT PORT than the one use below : 2090
  • JVM 6 required
  • The following module must be deployed : jmx-remoting.sar/ (if not available, get one in official JBOSS packaging jboss-5.1.0.GA)
  • modify the file ./server/default/deploy/jmx-remoting.sar/META-INF/jboss-service.xml to set the port
    <?xml version="1.0" encoding="UTF-8"?>
    <server>
       <mbean code="org.jboss.mx.remoting.service.JMXConnectorServerService"
          name="jboss.remoting:service=JMXConnectorServer,protocol=rmi"
          display-name="JMX Connector Server (RMI)">
               <attribute name="BindAddress">10.104.65.101</attribute>
                <attribute name="RegistryPort">1090</attribute>
       </mbean>
    </server>
  • Use the network interface using the option : -Djava.rmi.server.hostname=...

=> We will monitor JBOSS using JMX with 2 ports ! 1090 & 2090, 1090 for jvm mbeans, and 2090 for jboss mbeans

For JBOSS < 7.x & >= 6

JAVA_OPTS=$JAVA_OPTS" -Dcom.sun.management.jmxremote"
JAVA_OPTS=$JAVA_OPTS" -Djboss.platform.mbeanserver"
JAVA_OPTS=$JAVA_OPTS" -Djavax.management.builder.initial=org.jboss.system.server.jmx.MBeanServerBuilderImpl"
JAVA_OPTS=$JAVA_OPTS" -Dcom.sun.management.jmxremote.port=2500"
JAVA_OPTS=$JAVA_OPTS" -Dcom.sun.management.jmxremote.authenticate=false"
JAVA_OPTS=$JAVA_OPTS" -Dcom.sun.management.jmxremote.ssl=false"

TAKE CARE, to avoid error messages (ignored by processing), add jboss client jars to classpath

For Jetty

Use standard JSR 160 jmxrmi connection, but jetty mbeans must be enabled as by adding such block in jetty.xml configuration file, and setting all "StatsOn" to true :

<Call id="MBeanServer" class="java.lang.management.ManagementFactory" name="getPlatformMBeanServer"/>

<Get id="Container" name="container">
  <Call name="addEventListener">
    <Arg>
      <New class="org.mortbay.management.MBeanContainer">
        <Arg><Ref id="MBeanServer"/></Arg>
        <Call name="start" />
      </New>
    </Arg>
  </Call>
</Get>

works at least for jetty 6.1.x. jetty-management.jar must be added to the classpath if not already present.

For JBOSS 7.x

jboss-client.jar must be added to the classpath

To specify the right management listening network interface

 JAVA_OPTS="$JAVA_OPTS -Djboss.bind.address.management=10.134.115.167"
test@testhost ~/servers/jboss/bin $ ./add-user.sh 

What type of user do you wish to add? 
 a) Management User (mgmt-users.properties) 
 b) Application User (application-users.properties)
(a): a

Enter the details of the new user to add.
Realm (ManagementRealm) : 
Username : admin
Password : 
Re-enter Password : 
The username 'admin' is easy to guess
Are you sure you want to add user 'admin' yes/no? yes
About to add user 'admin' for realm 'ManagementRealm'
Is this correct yes/no? yes
Added user 'admin' to file '/opt/servers/jboss-as-7.1.1.Final/standalone/configuration/mgmt-users.properties'
Added user 'admin' to file '/opt/servers/jboss-as-7.1.1.Final/domain/configuration/mgmt-users.properties'

Small checks with JBOSS 7

using jconsole :

  ./jboss-as-7.1.1.Final/bin/jconsole.sh
     service:jmx:remoting-jmx://10.134.115.167:9999    username = admin  password = ""

  if local jboss : 
  jconsole -J-Djava.class.path=/home/dcr/.gentoo/java-config-2/current-user-vm/lib/jconsole.jar:/home/dcr/.gentoo/java-config-2/current-user-vm/lib/tools.jar:/home/dcr/servers/jboss-as-7.1.1.Final/lib/jboss-client.jar

using JAJMX :

 $ java -classpath ./bin/client/jboss-client.jar:/opt/analysis/analysis.jar com.orange.analysis.Main
 Welcome to Scala version 2.10.0 (Java HotSpot(TM) 64-Bit Server VM, Java 1.7.0_09).
 Type in expressions to have them evaluated.
 Type :help for more information.

 scala> val jmx = jajmx.JMX("10.134.115.167", 9999, Some("admin"))
 jmx: fr.janalyse.jmx.JMX = fr.janalyse.jmx.JMXclassicalImpl@7ccea5c6

 scala> jmx.whoami
 res0: Option[fr.janalyse.jmx.ASSignature] = Some(JBossSignature(7.1.1.Final,/home/dcr/servers/jboss-as-7.1.1.Final/standalone,jboss.as))

More Repositories

1

jassh

High level scala SSH API for easy and fast operations on remote servers.
Scala
71
star
2

code-examples-manager

Software tool to manage your notes, scripts, code examples, configs,... to publish them as gists or snippets
Scala
37
star
3

zio-lmdb

Lightning Memory Database (LMDB) for scala ZIO
Scala
36
star
4

sotohp

Photos management
Scala
27
star
5

scala-drools-dummy-project

Minimalist scala drools project
Scala
19
star
6

coursier-launcher

coursier docker container for efficient application or service download and startup
Makefile
9
star
7

zwords

A wordle game for communities
Scala
8
star
8

jaseries

scala API for time numerical series operations.
Scala
7
star
9

primes

Playing with primes using scala language. Draw Ulam spiral, ...
Scala
7
star
10

zio-worksheet

Simplified ZIO user experience in REPL, worksheet or script contexts
Scala
6
star
11

bootstrap

scala script bootstrap mechanism with #include support
Scala
6
star
12

the-weakest-link

Scala
4
star
13

custom-collection

Custom scala collection examples
Scala
4
star
14

scala-dummy-project

scala dummy project with standalone executable jar
Shell
3
star
15

drools-scripting

Drools made easy to use for scripting or testing purposes
Scala
2
star
16

codingame-with-scalakit-example

codingame scalakit example using git submodule to reference the scalakit
Scala
2
star
17

simple-plugin-architecture

Scala simple plugin architecture (with plugin automatic compilation if required)
Scala
2
star
18

exproxy

a 2005 personal project...
Java
2
star
19

cntlm

dockerized cntlm
Shell
2
star
20

primes-scalatra-app

Scala
1
star
21

naturalsort

scala naturalsort algorithm
Scala
1
star
22

web-echo

A websocket/webhook JSON data recorder with API
Scala
1
star
23

akka-sandbox

temporary project to test and learn AKKA 2
Scala
1
star
24

advent-of-code-2023

Scala
1
star
25

bullyboy

sha1 brute force attack
Scala
1
star
26

the-rules-for-good-code-examples

Several rules to write the best possible source code examples
1
star
27

data-recorder

Scala
1
star
28

advent-of-code-2020

Scala
1
star
29

jenkins-phantomjs-slave

jenkins slave with phantomjs 1.9 docker image
1
star
30

dock-primesui

Shell
1
star
31

jenkins

Jenkins docker image
Shell
1
star