package ai.h2o.api;
import io.grpc.Server;
import io.grpc.ServerBuilder;
import water.AbstractH2OExtension;
import water.H2O;
import water.util.Log;
import java.io.IOException;
/**
*/
public class GrpcExtension extends AbstractH2OExtension {
private int grpcPort = 0; // 0 means that GRPC service should not start
private Server netty;
@Override
public String getExtensionName() {
return "GRPC";
}
@Override
public void printHelp() {
System.out.println(
"\nGRPC extension:\n" +
" -grpc_port\n" +
" Port number on which to start the GRPC service. If not \n" +
" specified, GRPC service will not be started."
);
}
@Override
public String[] parseArguments(String[] args) {
for (int i = 0; i < args.length - 1; i++) {
H2O.OptString s = new H2O.OptString(args[i]);
if (s.matches("grpc_port")) {
grpcPort = s.parseInt(args[i + 1]);
String[] new_args = new String[args.length - 2];
System.arraycopy(args, 0, new_args, 0, i);
System.arraycopy(args, i + 2, new_args, i, args.length - (i + 2));
return new_args;
}
}
return args;
}
@Override
public void validateArguments() {
if (grpcPort < 0 || grpcPort >= 65536) {
H2O.parseFailed("Invalid port number: " + grpcPort);
}
}
@Override
public void onLocalNodeStarted() {
if (grpcPort != 0) {
ServerBuilder sb = ServerBuilder.forPort(grpcPort);
RegisterGrpcApi.registerWithServer(sb);
netty = sb.build();
try {
netty.start();
Log.info("Started GRPC server on localhost:" + grpcPort);
} catch (IOException e) {
netty = null;
throw new RuntimeException("Failed to start the GRPC server on port " + grpcPort, e);
}
Runtime.getRuntime().addShutdownHook(new Thread() {
@Override
public void run() {
if (netty != null) {
// Use stderr here since the logger may have been reset by its JVM shutdown hook.
System.err.println("*** shutting down gRPC server since JVM is shutting down");
netty.shutdown();
System.err.println("*** server shut down");
}
}
});
}
}
}