Archivo de la categoría: Code snippets

EasyRPC: crea fácilmente servicios RPC en puro Java

Acabo de publicar una versión inicial de EasyRPC en GitHub.  EasyRPC es una librería que automáticamente crea servicios y clientes web en tiempo de ejecución para Java.

Las características que destaco son:

  • Fácil de adoptar y usar. Descarga las librerías y úsalas directamente en el código para crear servicios web como cualquier otra clase Java, sin necesidad de lidiar con las complejidades de la serialización y el envío de datos.
  • Comunicación a través de HTTP y AMQP 1.0. Extensible a otros protocolos de comunicación.
  • Serialización a través de JSON-RPC 2.0. Extensible a otras especificaciones (SOAP, ProtoBuf…)

Todo ello, insistiendo, programando simples clases Java de la misma manera en que se programarían para ser ejecutadas en local.

A continuación se muestra un ejemplo de uso:

Programación del servidor

Paso 1: crea una interfaz con los métodos de tu servicio.

public interface IFace {
    int add(int a, int b);
    String concat(String s1, String s2);
    int[] doubleArray(int[] arr);
}

Paso 2: implementa la el servicio como una clase Java corriente que se fuera a ejecutar en local.

public class Implementation implements IFace {
    @Override
    public int add(int a, int b) {
        return a+b;
    }
    @Override
    public String concat(String s1, String s2) {
        return s1+s2;
    }
    @Override
    public int[] doubleArray(int[] arr) {
        for(int i = 0 ; i < arr.length ; i++) {
            arr[i] = arr[i] * 2;
        }
        return arr;
    }
}

Paso 3: instancia el servidor, especificando el protocolo de comunicación y el tipo de serialización.

Ejemplo 1: JSON-RPC 2.0 a través de HTTP

RpcServer server = new RpcServer(
            new HttpService(8080,"/rpc"),
            new JSONCallee());

Ejemplo 2: JSON-RPC 2.0 a través de AMQP 1.0:

RpcServer server= new RpcServer(
      new AmqpService(
              new URI("amqp://localhost:5672"),
              "rpcQueue"),
      new JSONCallee());

Paso 4: registra  el servicio a través de la clase que lo implementa, e inicia el servidor.

server.addEndpoint(new Implementation());
server.start();

Uso del cliente

Paso 1: obtén la interfaz IFace que describe el servicio a ejecutar. Ésta debe ser proporcionada por el proveedor, compartiendo, por ejemplo, el código fuente o un archivo JAR.

Paso 2: instancia el generador de clientes. En el ejemplo, habilita la comunicación a través de HTTP y la serialización a través de JSON-RPC 2.0.

ClientFactory clFact =
     new ClientFactory(
             new HttpClient(
                     "server.address.com",
                     8080, "/rpc"),
     new JSONCaller());

Paso 3: instancia el cliente.

IFace ws = (IFace) clFact.instantiate(IFace.class);

Paso 4: usa el servicio:

int result = ws.add(2,3);
String completo = ws.concat("Hola", " mundo!");

Agregar datos para una serie temporal con MongoDB

Supongamos una colección de datos en MongoDB que contiene documentos con una estructura similar a la siguiente, pertenecientes a un sistema de monitorización que guarda qué porcentaje de CPU consume cada proceso:

{ "proceso" : "1234",
  "timestamp" : 14567888841,
  "cpu" : 31.3 }

{ "proceso" : "33212",
 "timestamp" : 14567888941,
 "cpu" : 104 }

{ "proceso" : "1234",
 "timestamp" : 14567898381,
 "cpu" : 28.5 }

// etc...

Siendo “timestamp” una marca de tiempo. Por ejemplo, el número de milisegundos desde el 1/1/1970 00:00 UTF (System.currentTimeMillis en Java).

Si quisiéramos crear una serie temporal con, por ejemplo, el consumo medio de CPU del proceso ‘1234’ en bloques de 5 minutos (300.000 milisegundos), podríamos usar el framework de agregación de MongoDB enviando la siguiente petición (función aggregate):

[{ "$match":{
   "proceso": "1234"
 }},
 {"$group" : {
   "_id" : {
      "$subtract" : ["$timestamp" ,
                    {"$mod" : [ "$timestamp",
                                 300000 ]
                    }]
   },
   "cpu" : {"$avg": "$cpu" }
 }}]

Esta orden nos devolvería un array con todos los elementos de la serie de tiempo, similar al siguiente:

[{ "_id" : 14742000000, "cpu" : 22.33 },
 { "_id" : 14742300000, "cpu" : 12.30 },
 { "_id" : 14742600000, "cpu" : 33.75 },
 { "_id" : 14742900000, "cpu" : 10.69 },
 { etc... }}