Monitor the internal state of Java programs with Kubernetes

Introduction

This article is a reminder of how Kubernetes checks the status of a particular Java class at regular intervals and kills the pod if there is a problem. For more information on Kubernetes Liveness Probe, please see here (https://kubernetes.io/docs/tasks/configure-pod-container/configure-liveness-readiness-probes/#define-a-tcp-liveness-probe). ..

Java implementation

Monitored class

For testing purposes, implement ʻisAlive () == false` 10 seconds after the instance is created.

SomeResource.java


public class SomeResource {
  final long createdTime;

  public SomeResource() {
    this.createdTime = System.currentTimeMillis();
  }
  public boolean isAlive() {
    return System.currentTimeMillis() - createdTime < 10000;
  }
}

Monitoring endpoint

Implement to return the response code 200 when SomeResource # isAlive () == true and 500 when false.

HeartBeat.java


import com.sun.net.httpserver.HttpServer;
import java.io.IOException;
import java.net.InetSocketAddress;

public class HeartBeat {
  private final SomeResource target;
  private HttpServer httpServer;
  private final int port;

  public HeartBeat(SomeResource target, int port) {
    this.target = target;
    this.port = port;
  }

  void start() throws IOException {
    httpServer =
        HttpServer.create(new InetSocketAddress(port), 0);
    httpServer.createContext("/heartbeat", httpExchange -> {
      int responseCode;
      if (target.isAlive()) {
        responseCode = 200;
      } else {
        responseCode = 500;
      }
      byte[] responseBody = String.valueOf(target.isAlive()).getBytes(StandardCharsets.UTF_8);
      httpExchange.getResponseHeaders().add("Content-Type", "text/plain; charset=UTF-8");
      httpExchange.sendResponseHeaders(responseCode, responseBody.length);
      httpExchange.getResponseBody().write(responseBody);
      httpExchange.close();
    });
    httpServer.start();
  }

  void stop() {
    httpServer.stop(0);
  }
}

Main class

Main.java


import java.util.concurrent.CountDownLatch;

public class Main {

  public static void main(String[] args) {
    final CountDownLatch latch = new CountDownLatch(1);
    SomeResource resource = new SomeResource();
    HeartBeat heartbeat = new HeartBeat(resource, 1234);//Use port 1234

    Runtime.getRuntime().addShutdownHook(new Thread() {
      @Override
      public void run() {
        heartbeat.stop();
        latch.countDown();
      }
    });

    try {
      heartbeat.start();
      latch.await();
    } catch (Exception e) {
      e.printStackTrace();
      System.exit(-1);
    }
  }
}

Test endpoints with curl

Immediately after creating a SomeClass instance

console


$ curl --dump-header - http://localhost:1234/heartbeat
HTTP/1.1 200 OK
Date: Tue, 02 Jul 2019 07:24:20 GMT
Content-type: text/plain; charset=UTF-8
Content-length: 4

true

10 seconds later

console


$ curl --dump-header - http://localhost:1234/heartbeat
HTTP/1.1 500 Internal Server Error
Date: Tue, 02 Jul 2019 07:24:30 GMT
Content-type: text/plain; charset=UTF-8
Content-length: 5

false

Deploy to Kubernetes

The steps to create a container and push to the registry are omitted.

deployment.yaml


apiVersion: apps/v1
kind: Deployment
metadata:
  name: java-resource-watch-test
spec:
  replicas: 1
  selector:
    matchLabels:
      app: java-resource-watch-test
  template:
    metadata:
      labels:
        app: java-resource-watch-test
    spec:
      containers:
      - name: java-resource-watch-test
        image: some_registry/test:latest
        livenessProbe:
          httpGet:
            path: /heartbeat
            port: 8080
            httpHeaders:
            - name: Custom-Header
              value: HealthCheck
          initialDelaySeconds: 1
          periodSeconds: 1

kubectl apply -f ./deployment.yaml

You can see that the pod ends and restarts as soon as the SomeResource expires.

Summary

I was able to restart the pod depending on the status of the class and thread. There are various other methods such as a sidecar model using JMX, but I think the method introduced in this section is easy and flexible.

Recommended Posts

Monitor the internal state of Java programs with Kubernetes
Calculate the similarity score of strings with JAVA
CI the architecture of Java / Kotlin applications with ArchUnit
Organizing the current state of Java and considering the future
Check the behavior of Java Intrinsic Locks with bpftrace
A survey of the Kubernetes native Java framework Quarkus
The story of making dto, dao-like with java, sqlite
Replace only part of the URL host with java
Monitor the clipboard with JNA
[Java] Simplify the implementation of data history management with Reladomo
Explain the benefits of the State pattern with a movie rating
Be sure to compare the result of Java compareTo with 0
[Java] Delete the elements of List
[Java1.8 +] Get the date of the next x day of the week with LocalDate
[Java version] The story of serialization
Follow the link with Selenium (Java)
A story about hitting the League Of Legends API with JAVA
The point of addiction when performing basic authentication with Java URLConnection
Overwrite upload of file with the same name with BOX SDK (java)
Is the version of Elasticsearch you are using compatible with Java 11?
The origin of Java lambda expressions
The story of making a game launcher with automatic loading function [Java]
Let's express the result of analyzing Java bytecode with a class diagram
Be aware of the internal state (invariance) of objects and the side effects of methods
Check the domain by checking the MX record of the email address with java
[Java] Get MimeType from the contents of the file with Apathce Tika [Kotlin]
Monitor Java applications with jolokia and hawtio
Check the contents of the Java certificate store
Check the contents of params with pry
Examine the memory usage of Java elements
[Java] Get the day of the specific day of the week
Memo: [Java] Check the contents of the directory
Compare the elements of an array (Java)
I investigated the internal processing of Retrofit
[day: 5] I summarized the basics of Java
What are the updated features of java 13
Easily measure the size of Java Objects
Looking back on the basics of Java
Output of the book "Introduction to Java"
About the treatment of BigDecimal (with reflection)
The story of writing Java in Emacs
[Java] Make programs 10x faster with parallelStream
Format the contents of LocalDate with DateTimeFormatter
[Java] Check the number of occurrences of characters
[Java] [Spring] Test the behavior of the logger
Try using the Wii remote with Java
[Java] Get the date with the LocalDateTime class
Easily monitor the indoor environment-⑪ Obtain the illuminance with Java from BH1750FVI (substitute)-(I2C / Pi4J)-
Increment with the third argument of iterate method of Stream class added from Java9
Easily monitor the indoor environment-② Catch the Bluetooth LE advertisement signal with Java (Bluetooth LE / bluez-dbus)-
[Code] Forcibly breaks through the C problem "* 3 or / 2" of [AtCoder Problem-ABC100] with Java [Code]
Validate the identity token of a user authenticated with AWS Cognito in Java
The story of low-level string comparison in Java
JAVA: jar, aar, view the contents of the file
Back calculation of the transition of the internal seed of Random
The story of making ordinary Othello in Java
Verify the contents of the argument object with Mockito
About the description order of Java system properties
[LeJOS] Let's control the EV3 motor with Java
About the idea of anonymous classes in Java
The order of Java method modifiers is fixed