domingo, 23 de diciembre de 2018

Regla N°17 de la Ingeniería de Software: Primero el camino principal luego las excepciones


Todo proceso tiene un punto de inicio y un punto de finalización, una serie de pasos que hay que cumplir para llegar del punto A al punto B. Generalmente esto constituye el llamado “camino feliz” (Happy Path). Frecuentemente este camino tiene muchas bifurcaciones y situaciones a considerar para el software funcione de manera adecuada. El cómo estructuramos dichos “caminos” es lo que puede hacer a nuestro código enredoso, poco escalable y difícil de mantener (y crear).




Si es bien es cierto que uno se tiene que prepara para los fallos (para que el software falle) la ruta principal (de ejecución) debe ser un camino limpio y fácilmente trazable. Incluso desde el momento del diseño, no podemos dejarnos abrumar con todas las excepciones y giros posibles de la lógica de negocio, debemos diseñar el camino feliz, y asumir que habrá excepciones en algún momento. Esto es porque si bien el camino principal suele ser sencillo, los recovecos, bifurcaciones y excepciones suelen ser muchas, muy variadas y a veces difíciles de ver, si el cambio principal y los secundarios están entrelazados obtendremos un código sumamente difícil de comprender.




Repasemos un poco de la historia de los controles de errores en los lenguajes, para entender como interfieren en la flujo de un sistemas.

El siguiente ejemplo es de C (Extraído de https://en.wikibooks.org/wiki/C_Programming/Error_handling)

Ejemplo de código en C

  
01
02
03
04
05
06
07
08
09
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
#include <stdio.h>        /* perror */
#include <errno.h>        /* errno */
#include <stdlib.h>       /* malloc, free, exit */
 
int main(void)
{
 
    /* Pointer to char, requesting dynamic allocation of 2,000,000,000
     * storage elements (declared as an integer constant of type
     * unsigned long int). (If your system has less than 2 GB of memory
     * available, then this call to malloc will fail.)
     */
    char *ptr = malloc(2000000000UL);
 
    if (ptr == NULL) {
        perror("malloc failed");
        /* here you might want to exit the program or compensate
           for that you don't have 2GB available
         */
    } else {
        /* The rest of the code hereafter can assume that 2,000,000,000
         * chars were successfully allocated...
         */
        free(ptr);
    }
 
    exit(EXIT_SUCCESS); /* exiting program */
}
 

  
#include <stdio.h>        /* perror */
#include <errno.h>        /* errno */
#include <stdlib.h>       /* malloc, free, exit */

int main(void)
{

    /* Pointer to char, requesting dynamic allocation of 2,000,000,000
     * storage elements (declared as an integer constant of type
     * unsigned long int). (If your system has less than 2 GB of memory
     * available, then this call to malloc will fail.)
     */
    char *ptr = malloc(2000000000UL);

    if (ptr == NULL) {
        perror("malloc failed");
        /* here you might want to exit the program or compensate
           for that you don't have 2GB available
         */
    } else {
        /* The rest of the code hereafter can assume that 2,000,000,000
         * chars were successfully allocated... 
         */
        free(ptr);
    }

    exit(EXIT_SUCCESS); /* exiting program */
}
Antes de nada recordemos algunas cosas de C.

  • C no tiene un tipo booleano, cualquier cosas diferente de cero es verdadero y cero es falso.
  • C solo permite pasar parámetros por valor, si queremos modificar el valor contenido en una dirección de memoria tenemos que pasarla mediante un puntero (que a su vez se pasa por valor).
  • Las funcionen de C generalmente devuelve un puntero a un resultado, o cero en el caso que no hayan tenido éxito, también pueden devolver un valor numérico y devolver un resultado en un putero pasando como parámetro.

Esto genera un problema puesto que una función tiene que devolver dos cosas, primero indicar si ha tenido éxito o no, y después un valor con el resultado. Una funciona solo y exclusivamente debiera devolver su resultado, que falle por cualquier motivo, es una circunstancia excepcional que no debiera estar involucrado en su resultado.

C no tiene un control de errores establecido como otros lenguajes modernos, esto es que si ocurre un fallo, posiblemente no nos demos cuenta (si no lo revisamos), y el programa siga corriendo hasta que comience a suceder cosas extrañas y falle al querer acceder a una posición de memoria prohibida (lo que se conoce por como segment fault). Esto puede ocurrir bastante lejos, en líneas de código y en tiempo de ejecución, desde donde está realmente el problema, con lo que es terriblemente difícil diagnosticar este tipo de problemas.

Lo anterior provoca que tenga validarse el resultado de cada función antes de poder usarlo, con lo que después de cada llamada, debe hacer una serie de sentencias de verificación. veámoslo en el ejemplo:

Análisis de la preservación de memoria

  
1
2
3
4
5
6
7
8
char *ptr = malloc(2000000000UL);
 
if (ptr == NULL) {
    perror("malloc failed");
    /* here you might want to exit the program or compensate
       for that you don't have 2GB available
     */
}
 

  
char *ptr = malloc(2000000000UL);

if (ptr == NULL) {
    perror("malloc failed");
    /* here you might want to exit the program or compensate
       for that you don't have 2GB available
     */
}
El objetivo es reservar un número determinado de memoria, la función nos devolverá NULL (que es una constante para cero) o una dirección de memoria en caso contrario, aunque el ejemplo es trivial vemos que debemos comparar el resultado de la función siempre que la usemos para estar seguros que se nos regresa una valor apropiado. si usamos la función N veces, debemos comprobar el resultado N veces y prácticamente así con todas las funciones que lleguemos a usar. Esto fue una práctica común de programación durante mucho tiempo.

El problema es que nuestro código se llenaba de condicionales (if) para verificar resultados y no solo eso sino que de alguna forma las funciones que creábamos debieran considerar esas situación, con lo que estamos obligados a implementarlas de igual manera, es decir debíamos devolver de alguna forma, ya sea como resultado de la función o como un parámetro de salida (en forma de puntero), si la función a tenido éxito y por otro lado el resultado.

Una vez que hemos establecido que debemos comprobar si una funciona ha tenido éxito antes de poder usar su resultado, tenemos el problema de que debemos hacer si ha fracaso y como comunicar al usuario el motivo del fracaso. Evidentemente debemos interrumpir el flujo del programa, pudiéramos volver a intentarlo o podríamos retornar a la función llamadora, en cualquier caso debemos usar una estructura if, de forma más o menos complica, y que en un determinado momento, haría que nuestro código se convergiera en código espagueti.

En lenguajes más modernos las situaciones inesperadas o errores se controlan fuera del flujo principal, son las llamadas excepciones, cuya estructura en general es parecida a esta (esta es en c#, sacado de https://docs.microsoft.com/en-us/dotnet/csharp/programming-guide/exceptions/)

Ejemplo de código en C#

  
01
02
03
04
05
06
07
08
09
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
class ExceptionTest
{
    static double SafeDivision(double x, double y)
    {
        if (y == 0)
            throw new System.DivideByZeroException();
        return x / y;
    }
    static void Main()
    {
        // Input for test purposes. Change the values to see
        // exception handling behavior.
        double a = 98, b = 0;
        double result = 0;
 
        try
        {
            result = SafeDivision(a, b);
            Console.WriteLine("{0} divided by {1} = {2}", a, b, result);
        }
        catch (DivideByZeroException e)
        {
            Console.WriteLine("Attempted divide by zero.");
        }
    }
}
 

  
class ExceptionTest
{
    static double SafeDivision(double x, double y)
    {
        if (y == 0)
            throw new System.DivideByZeroException();
        return x / y;
    }
    static void Main()
    {
        // Input for test purposes. Change the values to see
        // exception handling behavior.
        double a = 98, b = 0;
        double result = 0;

        try
        {
            result = SafeDivision(a, b);
            Console.WriteLine("{0} divided by {1} = {2}", a, b, result);
        }
        catch (DivideByZeroException e)
        {
            Console.WriteLine("Attempted divide by zero.");
        }
    }
}
La estructura es try/catch/finally. lo interesante de esta estructura es que mantiene el flujo principal de la proceso dentro de la instrucción try, mientras que la gestión de errores y situaciones anormales se mantiene dentro de instrucciones catch (una por cada tipo de excepción)


Analicemos la primera función

Función SafeDivision

  
1
2
3
4
5
6
static double SafeDivision(double x, double y)
{
    if (y == 0)
        throw new System.DivideByZeroException();
    return x / y;
}
 

  
static double SafeDivision(double x, double y)
{
    if (y == 0)
        throw new System.DivideByZeroException();
    return x / y;
}
El objetivo de la función es realizar divisiones evitando dividir por cero, para lo cual valida si el segundo parámetro de entrada (el dividendo, la y), es un cero. Si es cero emerge una excepción. Esta es la principal diferencia, no se devuelve un parámetro de salida o un retomo de función indicando si tuvo éxito la ejecución, el único resultado posible de la función (como tal) es la misma división, si ocurriera algo inesperado se lanzaría una excepción que interrumpirá el flujo normal de ejecución.

Analicemos la segunda función

Función Main

  
01
02
03
04
05
06
07
08
09
10
11
12
13
14
15
16
17
static void Main()
{
    // Input for test purposes. Change the values to see
    // exception handling behavior.
    double a = 98, b = 0;
    double result = 0;
 
    try
    {
        result = SafeDivision(a, b);
        Console.WriteLine("{0} divided by {1} = {2}", a, b, result);
    }
    catch (DivideByZeroException e)
    {
        Console.WriteLine("Attempted divide by zero.");
    }
}
 

  
static void Main()
{
    // Input for test purposes. Change the values to see
    // exception handling behavior.
    double a = 98, b = 0;
    double result = 0;

    try
    {
        result = SafeDivision(a, b);
        Console.WriteLine("{0} divided by {1} = {2}", a, b, result);
    }
    catch (DivideByZeroException e)
    {
        Console.WriteLine("Attempted divide by zero.");
    }
}
El bloque try como tal no tiene ningún control de errores, ni ninguna sentencia condición que altere el flujo de ejecución

Bloque Try

  
1
2
result = SafeDivision(a, b);
Console.WriteLine("{0} divided by {1} = {2}", a, b, result);
 

  
result = SafeDivision(a, b);
Console.WriteLine("{0} divided by {1} = {2}", a, b, result);
los esperado es que la función devuelva la división y que se muestre el mensaje en pantalla.

El catch maneja (de forma aparte), cualquier tipo de error en el proceso.

Bloque Catch

  
1
2
3
4
catch (DivideByZeroException e)
{
    Console.WriteLine("Attempted divide by zero.");
}
 

  
catch (DivideByZeroException e)
{
    Console.WriteLine("Attempted divide by zero.");
}
Como vemos queda perfectamente clara cuál es el proceso principal y cuáles son las excepciones, siendo además extremadamente escalable.

El único problema que pudiéramos es cuantas bloque try/catch podemos usar y donde es idóneo colocarlas. Bueno aquí tener en cuenta un principio básico y es que las funciones deben ser lo más reducidas posibles, y realizar una exclusiva tarea, así que jamás debiéramos tener que anidar dos (o más) bloques try/catch. Sobre donde debemos poner los bloques try/catch, por el mismo motivo, funciones simplificada y únicas, las funciones mas internas (o privadas) realizarían menos actividades, con lo que posiblemente tengan una necesidad menor de controlar excepciones y si de emitirlos, así que se podría decir que las capas más internas de nuestra aplicación (private, internal) emiten excepciones y las mas externas los controlan.

Hasta ahora hemos repasado situación de control de errores o excepciones, situaciones anómalas, ¿Qué pasa cuando no son situaciones anormales, si no que con simplemente caminos a tomar, correctos, pero fuera del flujo principal de nuestra aplicación?

El objetivo primordial a evitar sigue siendo el mismo, evitar las sentencias condicionales y crear un camino claro hacia el flujo principal.

Aquí entra en juego la programación orientada objetos:

  • Mediante la herencia la POO, nos permite personalizar acciones, cada camino puede ser un objeto que sobrescriba las diferencias entre una necesidad (un camino y otro).
  • Mediante El principio de la Inversión de Control, nuestro camino principal está definido claramente, pero delega en objetos (que generalmente se establecer por Inyección de Dependencias), para realizar sus acciones. Es decir si queremos cambiar el comportamiento solo tenemos que cambiar el objeto concreto que realiza las opciones.

Por ejemplo, pensemos que estamos implementando el sistema de una tienda, El flujo principal podría ser, que el cliente selecciona un objeto y lo paga, con el pago pudiera haber una bifurcación según el medio de pago (efectivo, tarjeta, cheque), pero el flujo principal seria siempre el mismo, solo usaríamos un objeto que procesa el pago acorde a la necesidad presentada.

La regla final seria "Primero el camino principal luego las excepciones", esto aplicaría no solo a efectos de código, sino también a efectos de diseño.

jueves, 15 de noviembre de 2018

Consejos para realizar una entrevista de trabajo exitosa


Cuando un estudiante se quiere incorporar a la vida laboral, unos de los primeros problemas a los que se enfrenta son las entrevistas de trabajo. Es un nuevo escenario, con nuevos desafíos, en los que se aplican reglas diferentes a las que está acostumbrado. Como entrevistador y seleccionador en las áreas técnicas, te doy los siguientes consejos:



Llega de cinco a diez minutos antes. ¡Es increíble la poca importancia que se le da a la puntualidad! Si te va a entrevistar alguien de perfil técnico, ten por seguro que esta saturado de trabajo, y que está haciendo un “hueco” para poder entrevístate, lo cual hace tenga que mover sus compromisos. Si llegas tarde puede pasar que no te pueda entrevistar o que lo haga de mala gana. En lo personal me es imposible pensar en otra cosa durante la entrevista, si no tuvo la responsabilidad de llegar a tiempo a la entrevista de un trabajo, me resulta difícil de creer que sea acertado en sus tiempos y compromisos. Considera que llegar tarde predispone al entrevistado en tu contra y es una mala forma de comenzar.

Vístete adecuadamente, según el tipo de empresa que te va a entrevistar. A veces tenemos un estilo propio al que no queremos renunciar, lo sentimos como parte de nuestra identidad, y nuestra forma de ser, y eso está bien, pero lo cierto es que las empresas buscan personal que encajen con su forma de ser, su visión y su política. Si haces una entrevista en un lugar donde la norma de etiqueta es la formalidad, es mejor que busques dicha formalidad en la entrevista. Detalles sencillos como tener atado correctamente los cordones de los zapatos, la camisa colocada apropiadamente, y una imagen de cuidado personal adecuado, ayudan bastante a ofrecer una imagen acertada.

Infórmate muy bien de cuál es el giro y el área de intereses de la empresa que te esta entrevistando, y además intenta que quede patente en la entrevista que tienes dicha información. Los entrevistadores valoran mucho que se conozcan detalles de sus empresas, porque demuestran que el entrevistado tiene intereses y proactividad. No da muy buena imagen que el candidato no sepa nada de “donde esta” y “por qué vino”.

Cuando el entrevistador te pregunte algo, no conteste con monosílabos (“si”, “no”, “no sé”, “puede”), intenta siempre dar una explicación detallada, y que queden claro los “porqués”. El entrevistado quiere conocerte, conocer como piensas y como te desarrollas en un ambiente laboral.

Una de las reglas que asumí hace unos años, es no seleccionar gente que no pueda comunicarse apropiadamente. Para mí es muy importante que puedan interaccionar con compañeros y que quede claro que pueden comprender los requisitos y las necesidades apropiadamente. Tenlo mucho en cuenta, las capacidades de comunicación, son tan importantes como las capacidades técnicas.

Posiblemente te hagan una pregunta estilo “¿Dónde te ves dentro de cinco años?” La pregunta sobretodo es de interés profesional, piénsala bien, incluso llévala preparada. Contesta algo que le haga sentido al entrevistador y tenga que ver con vida empresarial. Hace unos meses un candidato me contesto que quería ser estrella de rock, lo cual es muy loable y sincero, pero fue bastante sorpréndete y sin ninguna relación con el puesto que yo pudiera valoras. El entrevistador siempre buscara algo que le diga que puedes ser una buena inversión a futuro, y que vale la pena apostar por ti. Hazle saber que es así.

Algunas otras preguntas comunes son, “¿Cómo trabajas en situaciones de estrés” y “¿Cómo trabajas en equipo?”. La primera pregunta tiene realmente mala fama, pero lo que realmente quiere saber un entrevistador es si eres capaz de reaccionar apropiadamente en un contingencia. Los sistemas informáticos son muy delicados, sobre todos si estos gestionan dinero, salud o algún tipo de seguridad (de la cual pueden depender incluso el patrimonio o la vida de alguna persona), es importante que en la contestación des algún ejemplo de una situación de estrés (profesional) que hayas vivido y como lograste superarla.

Sobre como trabajas en equipo, lo recomendable es que hables sobre las estructuras organizaciones en las que has trabajado y como te has relacionado en ellas (hablando de tus roles y de roles de las personas del equipo), también aprovecha para hablar de los procesos o métricas que has seguido. Destaca los puntos positivos del trabajo en equipo y los que han sido mas satisfactorios. Si quieres hablar de puntos negativos, es buena idea, siempre y cuando muestres como los superaste y no hables mal de tus compañeros (y jamás de de personas en particular). Una queja excesiva (y poco fundamentada) sobre determinados aspectos o personas puede generar una impresión negativa de tu forma de trabajar un equipo y lidiar con los problemas. Es increíble lo pequeño que es esta industria cuando llevas años trabajo, una vez entreviste a una persona que hablaba muy mal (pero muy mal) de su antiguo jefe, dio la casualidad que su jefe era un antiguo colaborador mío al que tenía en muy alta estima y con el que nunca tuve ningún problema (al contrario), lo cual me genero mucha controversia acerca de la sinceridad del candidato.

Seguramente también te pregunte el por que quieres este trabajo, contesta con sinceridad, pero también comenta aspectos que tengan que ver con tus intereses profesionales, y de crecimiento además comenta aspectos que tengan que ver con la misma empresa, igual puedes comentar intereses personales, pero no los maximices con respecto a los profesionales.

Habla claro de los aspectos tecnológicos que conoces bien, y se sincero con los que no conoces. Nunca digas “creo que si lo conozco”, o “creo que lo conozco con otro nombre”, es muy frustrante para un entrevistador, no poder decir definir que sabes o que no sabes, cualquier cosa que comience con un “creo”, el entrevistador lo va a convertir en un “no sabe”.

Siempre es conveniente tener experiencia en las tecnologías a tratar en la entrevista, si eres estudiante y no la tienes, intenta realizar proyectos personales que te provean de dicha experiencia, si no es posible, intenta tener cursos que demuestren que conoces la tecnología, y tampoco es posible, debes dejar en claro en la entrevista porque tienes las capacidades necesarias para obtener los conocimientos tecnológicos para el puesto, ya sea comparándolos con tecnológicas semejantes, o con desafíos parecidos que hayas superado.

Así pues infórmate bien de los requisitos tecnológicos que requiere el puesto, y aunque algunos nos los conozcas, es muy importante que tengas claros los nombres y para lo que sirve, un entrevistador de calidad, comprenderá que no es posible conocer todo, pero valora que digas cosas como “esta tecnología sirve para esto o aquello, aunque nunca le he manejado profesionalmente”.

Es importante la sinceridad, recuerda igualmente que seguramente habrá una prueba técnica para validar tus conocimientos, si no fuiste sincero el entrevistador se sentida “engañado” y tu credibilidad quedara en entredicho.

Muéstrate orgullo de tus conocimientos pero no seas prepotente, considera que la persona que te esta entrevistando posiblemente no solo sea experto en las tecnologías requeridas, sino en el negocio en las cuales se aplican dichas tecnologías, no te enzarces en discusiones estériles que no llevan a ninguna parte.

Posiblemente se interese por algunos aspectos de tu vida (dentro, claro de los que es prudente y normal). Realza aquellos que tienen que ve con la empresa o con tu profesión. Si te esta entrevistando alguien técnico, seguramente tenga muchos puntos en común, sobre los motivos por los cuales decidiste estudiar o dedicarte a esta profesión, con lo que es un tema para generar empatía y darte a conocer.

Si te ofrecen Café o agua, recházalos a no ser que le entrevistador está tomando algo, y solo acéptalo si dicho café o agua está cerca, por ejemplo si te una botella de agua (y te la dan en la mano), acéptala, eso ayuda a crear cercanía, pero si esto implicara a que el entrevistador tiene que levantarse o prepáralo es mejor no hacerlo.

Si tomaste agua o usaste una servilleta, asegúrate que no lo dejas en la mesa. No manches el lugar de la entrevista, eso da que pensar que eres poco cuidadoso con tu entorno, y con los detalles.

Cuida tu lenguaje corporal. Es bueno que te expreses moviendo las manos, eso da confianza. Si las manos están quietas, dan una sensación extraña, en cambio estarlas mostrado (de una manera no demasiado histriónica), da expresividad y ayuda a explicar las cosas mejor. Pero sobretodo no te muevas continuamente (sin darte cuenta), o comiences a hacer cosas como mover una pierna constantemente, golpear la mesa o mover la silla sin ningún motivo, eso da una sensación de inseguridad, y puede poner nervioso a tu entrevistador.

Unas de las cosas que se valora especialmente es que la gente se interese por el resultado de su entrevista, eso da a entender que es una persona que busca mejorar los aspecto negativos, y que no está esperando que las cosas simplemente pasen.

Espero que estos consejos te ayuden a superar las entrevista futuras con éxito.

domingo, 7 de octubre de 2018

El desarrollador, la empresa y la sociabilidad

Es común tener la imagen típica del desarrollador de software introvertido, con problemas para comunicarse apropiadamente, también es común el programador, que sin ser tímido, decide aislarse del resto del equipo para centrase únicamente en su trabajo. En ambos casos esa percepción y comportamiento es completamente erróneo, además de inservible tanto para las necesidades de la empresa, como para las necesidades mismas del desarrollador.

Los motivos para que se de esta imagen, y este comportamiento son diversos, en parte es porque clásicamente esta profesión es difícil de comprender para no los no introducidos en ella. si bien uno puede generar empatía, por ejemplo, con el trabajo un medico aunque no se fuera ducho en su profesión, no pasa pasaba lo mismo con el desarrollo de software. No se alcanzaba a comprender que era exactamente la construcción de sistemas, lo cual creaba una brecha entre el desarrollador del software y los consumidores de dicho software, esto es incluso a nivel empresarial y social. Mientras que es fácil establecer un entendimiento claro sobre las necesidades de un puesto de trabajo cualquiera entre empleado y empleador, no ocurría los mismo cuando el empleado es desarrollador y el empleador no (y esto era así en ambas direcciones).


El acercamiento general de la tecnología a la sociedad dado en los últimos años, y representado sobre todo por el uso de los teléfonos inteligentes (sorprendentemente por encima incluso de las necesidades de la informática en forma laboral), ha contribuido a que la brecha se disminuya en cierta forma, si bien no hay un entendimiento completo, si queda claro que se necesita de la capacidades de un desarrollador de software, o por lo menos del desarrollo de software en sí.

Desde el punto de vista de la misma profesión, creo que académicamente se fomenta la parte poco social e introvertida del desarrollo de software. Esta carrera requiere grandes dosis de introspección, es necesario dedicarle horas, trabajo y esfuerzo de forma individual, pero también es cierto que a nivel universitario, se enseñan a comprender las soluciones, antes de plantear los problemas, se enseña antes a programar, que a saber por qué se programa. En la carrera se instituye el uso de las matemáticas y de la lógica, como un eje central en el desarrollo de software, y esto se mantiene como un mantra posteriormente. Si bien las matemáticas y la lógica son importantes, no dejan de ser herramientas a usar, sin embargo el saber reconocer necesidades, a trabajar e interactuar correctamente en un equipo de trabajo, son habilidades que no se establecen apropiadamente en ámbito universitario.

Un ejemplo de lo anterior son la enseñanza de las base de datos. Las base de datos tiene una importancia empresarial enorme y digamos que son un solución directa para un problema en especifico, sin embargo quedan pobremente explicadas en la mayoría de las carreras universitarias. Cada vez que entrevisto a un candidato para un puesto de trabajo, el punto débil son las base de datos. Los nuevos programadores no comprende el alcance y la necesidades del uso de las base de datos, e incluso programadores veteranos, tratan a la base de datos como si fuera programación imperativa y estructura, en lugar de ser declarativa y lógica, llenando un sinfín de procedimientos almacenados con lógica de negocio, y teniendo graves temas de ineficiencia al acceder a los datos. En estos casos tanto la parte matemática/lógica como la parte de base de datos están explicadas (en distintas asignaturas), pero al no establecida y identificada correctamente la necesidad, no sirve la explicación de lo uno o de lo otro.

Ya en un ámbito empresarial el desarrollo de software puede encontrarse con las siguientes circunstancias:

  •  Poco entendimiento de los procesos y necesidades empresarial.
  •  poco entendimiento de la empresa sobre el rol de desarrollador de sistemas.
  •  Poca interacción y compresión de su propio equipo de trabajo


Más concretamente la asocialidad y falta de iteración personal del desarrollador pueden generar los siguientes problemas:

  • No entender claramente las requisitos del software a desarrollar, creando soluciones técnicamente correctas pero que no resuelven ningún problema real, con lo que se alagara la construcción del sistema de forma sustancial y se reducirá la calidad de este.
  • Fallar en su capacidad de negociación, lo cual encararía a dos escenarios:

    • Problemas para negociar tiempos, recursos y alcancen en sus proyectos, lo que acarreara retrasos, e inconformidad en el cliente y en la misma empresa.
    • Problemas para negociar un salario adecuado. no sabrá valoran adecuadamente cuánto vale su trabajo, aceptando una retribución inferior a la se merece. Este tema es más profundo de lo que parece, por que crea un precedente en mercado, si los desarrolladores de software no sabe negociar apropiadamente su salario, su precio o valoración bajara. Esto quiere decir que el sueldo que pueden cobrar los desarrolladores de software bajara en su conjunto, por que las empresas podrán pagar menos dinero para contratar a un programador (es como querer algo por un precio justo, cuando otra persona lo está regalando)

Los siguientes consejos pudieran ser útiles:

Es importante participar en la reuniones. A veces los desarrolladores adoptan una actitud pasiva esperando recibir instrucciones, sin saber muy bien porque están en una reunión en particular. En el mejor de los casos se quedan esperando a que alguien le ceda la palabra para poder intervenir. Es necesario que el desarrollado se “ceda” la palabra al es mismo, que busque activamente su participación, que exprese sus ideas y sus inquietudes sin que nadie se las pregunte, es completamente necesaria y beneficiosa la participación del desarrollo en la reuniones, y eso es algo que solo el mismo desarrollador (y nadie mas) puede provocar.

No solo hay que hacer un buen trabajo, tenemos que promocionar nuestro trabajo, hacer relevante nuestro trabajo, “No basta con ser bueno, hay que parecerlo”. frecuentemente los desarrolladores que realizan un trabajo de calidad, esperan que su trabajo hable por sí solo, lo cual generalmente no pasa. Un desarrollo de calidad no solo implica la resolución de las necesidades presentes sino estar preparado para solucionar las futuras (debe ser escalable), y eso algo que no se percibe inmediatamente, es algo que se tiene que se debe explicar (y vender correctamente).

también es necesario que realice actividades fuera de la oficina que le ayuden a socializar con los mismos compañeros, pueden ser deportes (como futbol o tenis), o algún otro tipo de actividad alejado de las computadores. En cualquier caso es muy recomendable hacer algún tipo de ejercicio físico, esto ayudara a desentrenarse y cuidar la salud (Es mejor tener un condicionamiento físico adecuado que nos ayude tanto a mantenernos despiertos, como a dormir cuando debamos, que a atiborrarnos de café o bebidas con cafeína, que solo nos alteran el sueño y el estado de ánimo).

Como conclusión, la proactividad es el elemento clave, un desarrollador debe ser el que inicie el proceso a su propio crecimiento, debe saber (y buscar) interactuar empresarialmente. Es muy raro se den oportunidad, por si solas, el desarrollador debe fabricar las suyas.

domingo, 12 de agosto de 2018

Recomendación: Elon Musk, el creador de Tesla, PayPal y SpaceX que anticipa el futuro de Ashlee Vance

Siendo objetivos Elon Musk, es una inversor de (muy) alto riesgo, el empresario del momento, que ha sabido ver oportunidades en mercados en los que es difícil triunfar, y además en los que parece que el éxito va y viene, siendo subjetivo Elon Musk esa construyendo pieza a pieza, el futuro de la humanidad.




Acabo de leer la biografía de Elon Musk (Elon Musk, el creador de Tesla, PayPal y SpaceX que anticipa el futuro de Ashlee Vance). Disfruto mucho leyendo biografías de personas y emprenderos que ha sabio marca un hito en el mercado.

Elon Musk es el fundador (o le gusta ser considerado como tal), de PayPal , SpaceX , Tesla y SolarCity. En mucho de esto casos se unió con personas más capacitadas en labores de ingeniería para poder llevar a cabo estos proyectos. Con lo que fuera, es justo reconocer que sin energía "impulsora" de Musk, posiblemente estas empresas nunca hubieras salido adelante, quedándose en buenas ideas o intenciones.

Sus dos grandes empresas son SpaceX, dedicada a la construcción cohetes aeroespaciales, que promete abaratar ese mercado en particular, y Tesla, un fabricante de coches eléctricos (hasta ahora) de lujo. Su otro "hijo", hasta ahora pequeño, es SolarCity, una empresa dedicada a la conversión y aprovechamiento de la energía solar, que posiblemente sea revolucionaria en su sector.

El objetivo declarado de Musk es llevar al hombre a Marte, no como una exploración, si no con la intención de convertir a Marte en una colonia de la humanidad.

Elon Musk parece querer llevar los relatos de ciencia ficción a la realidad, allí están las ideas de Ray Bradbury, Asimov, y Philip K. Dick , me atrevería decir que incluso de Futurama.

En cuanto a su vida privada, nació en Sudáfrica, donde fue un niño bastante introvertido, emigro en edad universitaria a Canadá, y posteriormente se estableció en estados unidos, donde comenzó su vida emprendedora con una empresa relacionada con el software y los anuncios por internet para posteriormente fundar lo que sería uno de los primeros bancos por internet. Todo eso se acabaría convirtiendo en PayPal (a través de fusiones). De esta experiencia acabo despedido y multimillonario, es una serie de declaraciones y eventos rocambolescos (como parece ser todo lo que hace). En cuanto a su parte personal, tiene cinco hijos y es divorciado tres veces (con su segunda esposa se caso dos veces).

En la parte que más nos interesa, la vida profesional, ha sido comparado en multitud de ocasiones con Steve Jobs , y la vedad es que si tiene bastantes semejanzas , aquí vamos a exponer varios aspecto en común, y analizar la diferencias y formas de trabajar que hacer especial a las empresas de Elon, de su competencia.

Personalidades excéntricas, que genera a la vez odio y admiración. El trato personal no parece ser una de las características más destacadas de Musk, siendo muy duro con los fallos, muy exigente con los resultados, y con tendencia a deshacerse muy rápido de lo que no le sirve, igualmente su misma energía y determinación contagia a sus empleados y hacen que sus ideas y aspiraciones sean compartidos por estos.

  • Una participación intensa en cada aspecto del desarrollo. A diferencia de otros CEOs (incluso otros que solo dirigen una sola empresa), Musk conoce el detalle de cualquier parte del desarrollo, incluso a un profundo nivel técnico.

  • Una disminución (hasta eliminación) de la burocracia y de las reuniones absurdas protocolarias . No hay nada que le moleste mas a Musk que una reunión sin sentido, con lo que las reuniones son cortos, mínimas, y deben tener un objetivo claro y conciso.

    Debido a las dos puntos anteriores Musk se implica extremadamente, y me refiero a que es capaz de martillear, o usar su transporte personal para traer materiales el mismo.

  • También busca tener el control de sus empresas. Tiene inversionistas, pero intenta postergar lo más posible la salidas a bolsa de sus empresas (sin duda, de su lección aprendida en PayPal o del mismo Steve Jobs, despedido de Apple).

  • Su control es tal que le lleva a querer ser reconocido como el impulsor absoluto y punto central de sus empresas. Esto es tal, que es común que el mismo se dirija a la prensa sin ningún tipo de filtro en sus declaraciones, creando sensaciones encontradas en su audiencia (su lenguaje es además, franco y directo, sin florituras, y generalmente con muchas groserías).

  • Por otro lado de rodea de gente de gran talento, ideas y capacidad , a la que no duda en despedir si caen de su gracia, aparentemente trabajar con Musk, es una montaña rusa, en cuanto a su favor.

  • Localizar los medios de producción cerca y si es posible también las materias primas, es decir las fabricas están en Estados Unidos, intentando crear y fomentar una económica local. Esto no solo se aplica a la fábrica de ensamblaje, si no a la creación de los mismos materiales a ensamblar.

  • Si no existe, algo lo inventa, y además lo hacen de forma barata , mientras que muchos fabricantes basan sus productos en el ensamblaje de los que sus proveedores puedan hacer, Musk tiene una idea clara de lo quiere, si no es posible, su equipo hace que sea posible. Mientras que otros CEOs se muestran razonables, en cuanto a los que es posible o no, Musk no cede en sus objetivos, ni en sus gustos personales, no busca soluciones en el mercado, sino en la inventiva de su equipo. Lo cierto es que esto hace que se desarrollen tecnologías nunca vistas que parecen sacadas del futuro. Esto me recuerda un poco a Steve Jobs, en que tenía una visión muy particular de cómo debiera verse sus productos, tal que se diseñaban primero la carcasa de sus iPhones, y después los ingenieros se debían de romper la cabeza, para ver como metían toda la potencia que quería Jobs en ese pequeño espacio.

  • Todo está conectado. Todo lo que dirige Musk, tiene un objetivo, ir a Marte, el destino final de su empresa de cohetes, SpaceX, es ese. Una vez allí necesitamos movernos con combustibles no fósiles, allí esta Tesla. Necesitamos crear energía, para eso está SolarCity. Todos sus pasos y adquisiciones van todos encaminados a ese objetivo.

Elon Musk, es una persona complicada, con muchos altibajos en su popularidad, pero realmente es el único que está haciendo una alternativa real y seria para el que hombre pueda vivir fuera de la tierra, lo cual es a veces tema de mofa, pero a cada paso que da, es algo que se antoja más realista y menos de ciencia ficción, en las próximas décadas, puede que veamos si Musk tenga razón o no.

Si estas interesado en Elon Musk, el creador de Tesla, PayPal y SpaceX que anticipa el futuro de Ashlee Vance, puedes encontrarlo en Amazon.

!Si esta entrada te ha gustado, compartela, y dale me gusta a la pagina de facebook!

domingo, 22 de julio de 2018

Curso Patrones de Software (Actualización)

Mientras revisaba el post anterior, sobre el curso "Criptografía, Certificados y Privacidad en Internet", decidí hacer algunas actualizaciones al curso de "Patrones de Software" realizado el año pasado.



Originalmente, el curso de Patrones de Software, tenia intención de ser un recorrido por diversos patrones, una especia de taller sobre cuando usar uno y usar otros, pero acabo evolucionando en una especie de charla de concienciación sobre la mantenibilidad del software, y la importancia de usar patrones para poder garantizarla, que una explicación exhaustiva de estos. Realmente, y académicamente hablando, siento que siempre es mejor comprender las situaciones y necesidades reales del mercado, que aprender datos sin un contexto en particular.

El curso duro tres sesiones de dos horas cada una, y relazaron charlas y talleres con respecto al uso de los patrones de software.

En su momento, compartir los ejercicios de los talleres (el código fuente), en esta actualización comparto las presentaciones realizadas y todo el material documental,

Los materiales del curso están en GitHub. Esperando que pudieran ser de utilidad, lo hago de código libre (tanto los ejemplos como la documentación). Se les puede dar el fin que se desee.

!Si esta entrada te ha gustado, compartela, y dale me gusta la pagina de facebook!

Los enlaces relativos al curso son:

La presentación del curso es la siguiente:


Acerca de este documento


La misión de este documento es exponer los objetivos, mecánica y temerarios planteados para el curso de CreSer “Patrones de Software”.


Objetivos del curso


Los patrones de software son soluciones previamente establecidas (y probadas como optimas) a problemas conocidos y repetitivos dentro del desarrollo de software.

El curso de “Patrones de Software” pretende proporcionar herramientas para crear un escenario en el que se favorezca la creación de software de calidad, escalable y funcional.

A la vez que se revisan conceptos básicos para la ingeniera de software (para establecer un contexto de inicio) se estudiaran una selección de los más útiles patrones de software. Por otro lado y a modo de complemento se revisar una colección de los “peores” patrones de software, o anti-patrones (comportamiento y metodologías perjudiciales para la construcción de sistemas), de forma que sirva como elementos comparativo.


Metodología


Se distribuirá el curso en tres sesiones de tres horas cada una en las cuales, después de una introducción de los temas a plantear, se realizan talleres prácticos de los patrones de software, los cuales serán realizados en equipos de a dos ( dos personas compartiendo una computadora ).

Requisitos


Es necesario una laptop por cada dos personas, y tener conocimientos promedios de programación en C#. La computadora debe tener instalador Visual Studio 2010 o superior.




  • Les proporcionare igualmente un script de Ruby para facilitar la configuración a base de datos, si desean usarlo, deben instalarse Ruby, si no deberán hacer la configuración manualmente.


Temario


  1. Presentación de objetivos

  2. El desarrollo de software en la empresa

  3. En este apartado se trataran temas propios de la ingeniera de software y el desarrollo de software en la empresa con intención de establecer un contexto previo

    a) Acerca de la ingeniería de software


    b) Escenarios dentro del desarrollo de software


    c) Construcción de una fábrica de software


  4. Acerca de los programación orientada a objetos

  5. Se analizara los principios básicos de la programación orientada a objetos, para establecer los fundamentos solos los que se sustentan los patrones de software

    a) Principios generales de la orientación a objetos


    b) Principios SOLID



  6. Introducción a los patrones de software


  7. Breve introducción a los patrones de software, su origen y su utilidad.

    1. Breve historia de los patrones de software.
    2. Tipos de patrones de software.
    3. Anti patrones de software.

  8. Explicación de patrones de software

  9. Hediondez del código


  10. En este apartado se trata la “hediondez del código”, un concepto por el cual un software que aparentemente funciona bien, oculta graves problemas en su interior que pueden emerger en cualquier momento. Se revisaran los siguientes conceptos


  11. Anti-patrones de software

  12. Los anti-patrones de software son la mejor forma de hacer algo mal. Aquí se estudiaran con intención de evitarlos.


    Los anti-patrones para estudiar a:

    • Base de datos como comunicador de procesos.
    • Clase Gorda.
    • Re-dependencia.
    • Acoplamiento secuencial.
    • Modelo de dominio anémico.
    • YAL (Yet Another Layer, y otra capa más).
    • Ancla del barco.
    • Código espagueti.
    • Reinventar la rueda.
    • No inventado aquí.
    • Otra reunión más lo resolverá.
    • Proyecto del día de la marmota.
    • Si funciona, no lo toques.

  13. Conclusiones

miércoles, 4 de julio de 2018

Curso Criptografía, Certificados y Privacidad en Internet


Este año he estado impartiendo un curso, llamado "Criptografía, Certificados y Privacidad en Internet". El curso en si es una charla de dos horas sobre diversos aspectos relacionados con el origen de la criptografía, internet y la seguridad en internet.




Los materiales del curso están en GitHub. Esperando que pudieran ser de utilidad, lo hago de código libre (tanto los ejemplos como la documentación). Se les puede dar el fin que se desee.

Los enlaces relativos al curso son:

Documento explicativo del curso


Presentación del curso


Enlace de GitHub de los materiales


La presentación del curso es la siguiente:

ACERCA DEL INSTRUCTOR


José Luis Bautista Martín, Ingeniero de Sistemas, con maestría en “investigación en ingeniería de Software”. Mi experiencia laboral en cuanto a desarrollo de software abarca desde tecnologías “legacy”, hasta tecnologías de vanguardia, poniendo siempre una especial atención en la construcción de software escalable, modular y sostenible. Igualmente estoy especializado en la interconexión de diversos sistemas y plataformas para conseguir una solución coherente entre la tecnología actual en producción y nuevas tecnologías del mercado.

Una de mis inquietudes actuales es simplificar el desarrollo de software, permitiendo mediante herramientas generadoras de código, patrones de software, programación orientada a aspectos o simplemente interfaces sencillas y claras que el programador se concentre en resolver los problemas propios de la solución a implementar (esto es, los requisitos de negocio a representar en forma de software) y no se tenga que preocupar de tareas repetitivas, generalidades de los sistemas, o problemas técnicos, que no hacen más que distraerle de sus verdaderos objetivos.

ACERCA DE ESTE DOCUMENTO


La misión de este documento es exponer los objetivos, mecánica y temerarios planteados, así como la documentación para el curso de CreSer “Criptografía, Certificados y privacidad en internet”.

OBJETIVOS DEL CURSO


Este curso tiene como objetivo, ser una introducción acerca de la realidad de la privacidad y seguridad en Internet, revisando los motivos y circunstancia (actuales) en la que esta es violada, para posteriormente presentar las herramientas de criptografía, y a los certificados como los medios actuales para garantizarla.

METODOLOGÍA


Sera una conferencia de dos horas, en la que la primera hora se comentara sobre las circunstancias actuales de la seguridad en Internet, y la segunda tendrá una escenario más práctico al usar las herramientas de criptografía y generación de certificados.

REQUISITOS


No requiere ningún requisito en especial, si los asistentes quieren acompañar al instructor en la realización de los ejemplos de criptografía, deberán llevar una laptop, pero no es imprescindible.

EJEMPLOS


Los ejemplos de creación de certificado se encuentran en estas carpetas:

  • Certificadora Inicial: Ejemplo de las estructura de certificadosantesde realizar los ejercicios.
  • Certificadora Final: Ejemplo de las estructura de certificadosdespuésde realizar los ejercicios.


Nota importante: Nunca use los certificados expuesto aquí como productivos, genere siempre sus propias llaves privadas.

CONTENIDO


  • Acerca del instructor
  • Acerca de este documento
  • Objetivos del curso
  • Contenido
  • Metodología
  • Requisitos
  • Introducción
  • Breve historia de las criptografía
  • Breve historia de Internet
  • Seguridad en internet
  • Privacidad en internet
    • Caso espionaje NSA
    • Caso del teléfono el terrorista de San Bernardino
    • Caso Cambridge Analítica
  • Tipos de criptografía
    • Criptografía simétrica
    • Criptografía asimétrica
  • Certificados
    • Entidades certificadoras
    • Entidades intermediarias
    • Certificados personales
    • Configuración de certificados con GnuGPG
  • Anexo I: Ejemplos de certificados
  • Anexo II: Extensiones de archivos criptográficos