Background
The opsunit framework allows to continuously run a number of JUnit unit tests and do some maintenance/repair work upon any failed test.
The latest addition to the test suite for the Appjangle platform is a simple unit test, which checks the remaining free memory on the server node. If the free memory goes beyond a certain threshold (e.g. 150 mb), some maintenance work is conducted in order to free memory on the node.
Since the server nodes are running a UNIX derivate, the Java unit test therefore needs to be able to determine the currently available system memory.
Problem
How to determine the available free system memory on a UNIX system from a Java program?
Solution
The first starting point is the ‘vmstat’ application. This application prints out all different kinds of information for the current system. Together with a few other GNU programs, it can be moulded to return the available free memory:
vmstat -s -S M | egrep -ie ‘memory|swap’ | grep ‘free memory’
It is possible to run this shell script from Java. There are multiple ways to achieve this, many of them troublesome and I ALWAYS do it wrong. Therefore I have assembled my hard-learned best practices (and those of others I could find) in the project java-start-process. Using this project, we can determine the free memory for a UNIX system using the following function:
public static int getFreeMemoryUnixInMb() { try { final String expr = Spawn .runCommand( new String[] { "/bin/bash", "-c", "vmstat -s -S M | egrep -ie 'memory|swap' | grep 'free memory'" }, null); // expr sth like " \t \t778 M free memory " final String[] elems = expr.split(" |\t"); for (final String elem : elems) { try { return Integer.valueOf(elem); } catch (final Throwable t) { } } throw new RuntimeException( "Could not find free memory within: Elements=" + Arrays.asList(elems) + " Raw Result=[" + expr + "]"); } catch (final Throwable t) { throw new RuntimeException(t); } }
Resources
vmstat :: Detect Problems That Can Adversely Affect System Performance