domingo, 26 de mayo de 2019

Supervisor técnico

En los proyectos actuales siempre veo roles que se repiten: jefe de proyecto, funcionales, técnicos, arquitectos y programadores. Con las técnicas de gestión ágiles aparece el product owner, el scrum master y el cliente (este ultimo nunca forma parte del equipo). Me falta alguien que creo que es vital para la culminación de un proyecto de desarrollo de software, el supervisor tecnico. Esta figura es el encargado de:


  • Diseño técnico.
  • Que los programadores sigan las especificaciones técnicas y los estilos de programación.
  • Ser el validador de que lo implementado es lo que realmente se ha indicado en los funcionales.

sábado, 20 de abril de 2019

Kafka con Spring Boot. Topicos y Colas.

Kafka es un gran framework que se usa para comunicación entre aplicaciones. El objetivo de este artículo no es estudiar las características de Kafka ni de Spring boot, para eso hay mucha documentación en las paginas web de cada framework. El objetivo de este articulo es explicar una forma sencilla de montar Kafka, de como usarlo para comunicar aplicaciones Spring boot, como realizar una comunicación por tópicos (es decir todos los consumidores escuchan el mensaje) y realizar comunicación por colas (es decir solo un consumidor escucha el mensaje) para los programadores que están acostumbrados a otros frameworks como ActiveMQ o RabbitMQ.

Kafka no funciona de la misma manera que los framework mas comunes(ActiveMQ o RabbitMQ) por lo que no hay una forma directa de hacer lo mismo pero en este artículo voy a describir como aplicar comportamientos equivalentes.


Para comprender correctamente este articulo necesitas tener conocimientos básicos de Docker y Spring boot.

La forma mas sencilla de montar un "servidor" de Kafka es usar Docker, se puede usar el siguiente fichero de docker-compose:


docker-compose.yml 

version: '3'
services:
  zookeeper:
    image: wurstmeister/zookeeper
    ports:
      - "2181:2181"
    hostname: zookeeper
  kafka:
    image: wurstmeister/kafka
    command: [start-kafka.sh]
    ports:
      - "9092:9092"
    hostname: kafka
    environment:
      KAFKA_ADVERTISED_HOST_NAME: localhost
      KAFKA_ZOOKEEPER_CONNECT: zookeeper:2181
      KAFKA_ADVERTISED_PORT: 9092
    volumes:
      - /var/run/docker.sock:/var/run/docker.sock
    depends_on:
      - "zookeeper"



Una vez ejecutado este fichero, ya esta disponible Kafka en el puerto 9092.

El código del productor de mensajes y de consumidor de mensajes esta en https://github.com/rumberomelo/productor-consumidor-basico

Si descargas el código y lo ejecutas (y has arrancado Kafka como indico al principio) puedes comprobar el funcionamiento mas sencillo, un productor que escribe un mensaje de texto que lee un unico consumidor. Para hacer funcionar el ejemplo solo tienes que hacer la siguiente petición:

http://localhost:9000/envia/mensaje?texto=hola

Esta petición hará que el productor escriba en el tópico de Kafka "TOPIC_EJEMPLO" el mensaje "hola". Puedes comprobar en el log del consumidor que lo ha leido ya que aparecera un mensaje como INFO 47114 --- [ntainer#0-0-C-1] com.rumberomelo.kafka.consumer.Consumer  : Se ha consumido el mensaje hola.

Este ejemplo muestra como un consumidor lee un mensaje que produce un productor. Si lanzaramos un consumidor exactamente igual pueden pasar dos cosas (depende de como se configure Kafka):

  • El nuevo consumidor es el unico que lee todos los mensajes de productor.
  • El nuevo consumidor siempre queda a la espera (nunca lee ningun mensaje) y el viejo consumidor lee todos los mensajes.
Esto se puede comprobar en el ejemplo https://github.com/rumberomelo/productor-dos-consumidores y ver que solo un consumidor lee el mensaje. Si aplicamos un pequeño cambio y cambiamos el nombre de los grupos de cada uno de los consumidores como indican estos dibujos:





Al arrancar de nuevo los ejemplos se puede comprobar como los dos consumidores reciben en mensaje mirando el log de los consumidores. Este comportamiento es igual al tópico de frameworks como RabbitMQ o ActiveMQ.

Volvemos a dejar el nombre de los grupos como estaba. ¿Como se hace para que un mensaje lo lea uno de los consumidores (no siempre el mismo)? Se hace indicando las particiones en las que se quiere dividir el tópico. Cuando un productor escribe en un tópico que no existe (que es lo que se ha hecho al principio de este articulo) se crea automáticamente sin particiones, si tienes varias particiones entonces los consumidores se reparten dichas particiones de tal manera que cada consumidor solo lee de una de las particiones asignadas y como un mensaje se puede colocar aleatoriamente en cualquier particiones ya se ha logrado que sea un consumidor cualquiera el que lea el mensaje.

Para probarlo, se debe entrar en el contenedor de Kafka:


$ docker exec -it articulokafta_kafka_1 bash

Se puede comprobar que no hay particiones:


$ kafka-topics.sh --describe --zookeeper zookeeper:2181 --topic TOPIC_EJEMPLO

Topic:TOPIC_EJEMPLO PartitionCount:1 ReplicationFactor:1 Configs:
Topic: TOPIC_EJEMPLO Partition: 0 Leader: 1001 Replicas: 1001 Isr: 1001

Se añaden dos particiones:


$ kafka-topics.sh --alter --zookeeper zookeeper:2181 --topic TOPIC_EJEMPLO --partitions 2


Al arrancar de nuevo el ejemplo https://github.com/rumberomelo/productor-dos-consumidores y dejar el nombre de los grupos como estaban originalmente, si se hace la prueba de lanzar varios mensajes entonces se puede comprobar como a veces los lee un consumidor y a veces otro.








jueves, 29 de noviembre de 2018

VisualVM OQL. Get size of objetcs between two size values

 select sum(map(heap.objects("[C"),function(heapString){
  if(sizeof(heapString) < 100 && sizeof(heapString) > 50){
    return sizeof(heapString);
  }
  else{   
    return 0;
  }
}));

lunes, 22 de octubre de 2018

Aprender las cosas como son

Cuando a alguien se le encarga gestionar el desarrollo de una aplicación (o parte de esa aplicación), su principal tarea es ver que falla de la tarea, como plantearla, como planificarla, etc.. y el gran problema es que el gestor esta obligado a hablar de asuntos tecnicos cuando se supone que un gestor "no debe saber nada" de tecnología.

Se debe abandonar los hábitos de poco esfuerzo (ser gestor y no querer saber nada técnico). No debe saber lo mismo que un técnico pero tiene que hablar el mismo idioma.

¿Como sabes que estas hablando el mismo idioma?
 - Si lo único que un gestor le dice a un técnico es "¿cuanto te queda?", "¿como vas?  y acto seguido le dice el gestor que le queda (se nota que no ha entendido la explicación de como va)". Esto es síntoma de que el gestor y el tecnico no hablan el mismo idioma.

Solución: Gastar tiempo del gestor y del tecnico y que el tecnico le explique al gestor como esta implementando la tarea. Ojo, el gestor nunca tiene que hacer "nada tecnico" pero debe ser capaz de entender lo que el tecnico le dice y ser capar de pedir cambios (en el idioma del tecnico).

domingo, 7 de octubre de 2018

Estimation by approach. Always usefull

Sometimes the project manager people think the agile methods cant be used in the projects developed by a traditional approach. The things are not always black or white, we can use agile methods for all kind of projects. For example, the estimation by approach, we can use it for estimating task in projects with a traditional way of work.

In addition, the estimation by approach is always the best way for estimating task if you want a real estimation. The one way for a real estimation is to know the time a developer have spent in some task. This is the great true and, in conclusion, the bes† way to estimate a task is to use the known duration of some task and use this duration for estimating other task.

The estimation by approach is very simple, if we know that a developer spend 3 days for completing a login screen and we suppose the list of costumer screen has four times the login screen size then a good estimation for a list of costumer screen is 12 days.

How you can see, we are using a estimation by approach without change the way of work. 

lunes, 1 de octubre de 2018

Desenredar los cables

Cuando has trabajado en varios proyectos de desarrollo de software de mediano-gran tamaño te das cuenta que la tendencia normal es que no exista documentación que te guíe por el código, los compañeros te ayudan pero como mejor saben (y cada uno a su manera), etc.. Esto hace que cuando se le pide a un programador que implemente sus primeras tareas este tenga la sensación de tener que "desenredar los cables" para poder empezar.

Al analizar esta situación en detenimiento, todo esto se traduce en muchos factores no deseados:


  • Insatisfacción y frustración del programador.
  • Costes de aprendizaje que se multiplican.
  • Sensación de mala estructura del proyecto.


Siempre se debe tener un mecanismo de formación "automático" (quiero decir que no necesite de una tercera persona, es decir se le puede decir al miembro del equipo "toma esto" y con lo que se le de entonces puede formarse) para que un miembro del equipo pueda consultarlo y pueda usarlo como guia.

El procedimiento para tener un mecanismo de formación automático es tener una documentación técnica apropiada. Esta documentación tiene que tener las siguientes características:


  • Estar escrita en un idioma de programadores. Lo cual garantiza que no se "hace larga de leer" y va directa al grano.
  • Estar escrita en un formato cómodo de leer para un programador. Recomiendo una pagina web antes que un documento de texto.
  • Que sea facil de mantener. Importante. Se debe mantener y que sea facil hacerlo ya que si no es facil de mantener entonces se abandonara.

miércoles, 19 de septiembre de 2018

Integración continua. Cuando lanzar las pruebas

¿Cuando se deben lanzar las pruebas automáticas? Existen muchas tendencias en función de un factor:

- Numero de cambios de código (Cada cuantos cambios de código se lanzan las pruebas):

  • Ante cualquier cambio: Tiene la ventaja de que se detectan mejor los fallos pero tiene la desventaja de que puede relentizar el desarrollo ya que hace que el programador se centre demasiado en las pruebas.
  • Ante cambios en una funcionalidad: Tiene la ventaja de favorecer el desarrollo pero si la funcionalidad es muy grande se corre el riesgo de no hacer las pruebas lo suficientemente buenas.
  • ....

Como se ve a medida que se amplia el ratio se gana en velocidad de desarrollo y se pierde en calidad de pruebas.


- Tiempo (se establece un tiempo periodo de ejecución para lanzar las pruebas)
  • Cada dia: Son pruebas bastante periódicas y pueden detectar un fallo antes. Lo malo es que es un tiempo fijo y corto y puede no tener en cuenta los ciclos de desarrollo (como un sprint de SCRUM)
  • Cada fin de semana: al ser mas tiempo es mas facil que se alinien con los ciclos de desarrollo pero se tarda mas en detectar un fallo.
  • ...

Como se ve a medida que se amplia el ratio se gana en alinear las pruebas con ciclos de desarrollo y se pierde en detección temprana de errores.

-...

Hay muchas tendencias y dentro de cada tendencia hay diversas opciones que pueden mejorar y empeorar un factor u otro. Es una locura entonces cual elegir. La mejor elección es no tener en cuenta los factores si no la que obtiene mejor resultado. Lo que sede hacer es elegir una tendencia y dentro de la tendencia elegir una opción, darle un tiempo y ver que resultados se obtienen. Si son malos resultados entonces probar con otra hasta que se de con la opción y la tendencia que mejor se ajuste al equipo y al tipo de producto.