Sarge

Sonatype helps open source projects to set up Maven repositories on https://oss.sonatype.org/

License

License

Categories

Categories

Net
GroupId

GroupId

net.jodah
ArtifactId

ArtifactId

sarge
Last Version

Last Version

0.3.2
Release Date

Release Date

Type

Type

jar
Description

Description

Sarge
Sonatype helps open source projects to set up Maven repositories on https://oss.sonatype.org/
Project URL

Project URL

http://github.com/jhalterman/sarge/
Source Code Management

Source Code Management

http://github.com/jhalterman/sarge/

Download sarge

How to add to project

<!-- https://jarcasting.com/artifacts/net.jodah/sarge/ -->
<dependency>
    <groupId>net.jodah</groupId>
    <artifactId>sarge</artifactId>
    <version>0.3.2</version>
</dependency>
// https://jarcasting.com/artifacts/net.jodah/sarge/
implementation 'net.jodah:sarge:0.3.2'
// https://jarcasting.com/artifacts/net.jodah/sarge/
implementation ("net.jodah:sarge:0.3.2")
'net.jodah:sarge:jar:0.3.2'
<dependency org="net.jodah" name="sarge" rev="0.3.2">
  <artifact name="sarge" type="jar" />
</dependency>
@Grapes(
@Grab(group='net.jodah', module='sarge', version='0.3.2')
)
libraryDependencies += "net.jodah" % "sarge" % "0.3.2"
[net.jodah/sarge "0.3.2"]

Dependencies

test (5)

Group / Artifact Type Version
org.testng : testng jar 6.5.2
com.google.inject : guice jar 3.0
ch.qos.logback : logback-classic jar 1.0.13
ch.qos.logback : logback-core jar 1.0.13
org.springframework : spring-context jar 3.2.4.RELEASE

Project Modules

There are no modules declared in this project.

Sarge

Build Status Maven Central License JavaDoc

Simple object supervision (for when stuff goes wrong)

Sarge creates supervised objects which automatically handle failures when they occur by performing retries, state resets, and failure escalation, allowing for easy and robust fault tolerance with little effort.

Usage

Sarge handles failures according to a Plan which takes an exception and directs Sarge to do something with it. Creating a Plan is straightforward:

Plan plan = Plans
  .retryOn(TimeoutException.class, 5, Duration.mins(1))
  .escalateOn(ConnectionClosedException.class)
  .rethrowOn(IllegalArgumentException.class, IllegalStateException.class)
  .make();

This Plan retries any method invocations that fail with a TimeoutException, escalates any ConnectionClosedExceptions, and rethrows any IllegalArgumentExceptions and IllegalStateExceptions.

Supervision

With our Plan in hand, we can create a supervised object:

Sarge sarge = new Sarge();
MailService service = sarge.supervised(MailService.class, plan);

Supervision is automatically applied according to the plan when any exception occurs while invoking a method against the object:

// Failures are handled according to the plan
service.sendMail();

Hierarchical supervision

Sarge can create a parent/child supervision hierarchy where the Supervisor's plan is applied to any failures that occur in the child:

class Parent implements Supervisor {
  @Override
  public Plan plan(){
    return Plans
      .retryOn(TimeoutException.class, 5, Duration.mins(1))
      .escalateOn(ConnectionClosedException.class)
      .make();
  }
}
 
Parent parent = new Parent(); 
Sarge sarge = new Sarge();
 
// Create a new Child that is supervised by the parent
Child child = sarge.supervised(Child.class, parent);

We can link additional supervisable objects into a parent-child supervision hierarchy, which will handle any failures that are escalated:

Parent parent = sarge.supervisable(Parent.class);
sarge.supervise(parent, uberParent);

More on plans

Aside from the Plans class, Plans can also be constructed directly by implementing the Plan interface and returning the desired Directive for handling each failure:

Plan plan = new Plan() {
  public Directive apply(Throwable cause) {
    if (cause instanceof TimeoutException)
      return Directive.Retry(5, Duration.min(1));
    if (cause instanceof ConnectionClosedException)
      return Directive.Escalate;
  }
};

Lifecycle hooks

Lifecycle hooks allow supervised objects to be notified prior to a supervision directive being carried out, allowing an object to reset its internal state if necessary:

class SupervisedService implements PreRetry {
  @Override
  public void preRetry(Throwable reason) {
    if (reason instanceof ConnectionClosedException)
      connect();
  }
}

3rd Party Integration

By default, supervised objects must be instantiated by Sarge since they require instrumentation. As an alternative, we can delegate instantiation of supervised objects to other libraries such as Spring or Guice by hooking into Sarge's SupervisedInterceptor. Have a look at the tests for examples on how to integrate 3rd party libraries.

Logging

Logging is provided via the slf4j API. Invocation exceptions are logged at the ERROR level and include only the exception message. Full exception logging can be enabled by setting the DEBUG log level for the net.jodah.sarge category.

Docs

JavaDocs are available here.

Limitations

Since Sarge relies on runtime bytecode generation to create supervised objects by subclassing them, it cannot supervise classes that are final, protected or private, or methods that are final or private.

Thanks

Sarge was inpsired by Erlang OTP's supervision trees and Akka's supervision implementation. Thanks to the their contributors for the great work.

License

Copyright 2012-2013 Jonathan Halterman - Released under the Apache 2.0 license.

Versions

Version
0.3.2
0.3.1
0.3.0