¿Qué son y para qué sirven? Lambda: Versiones y Alias

Utilizar funciones Lambda puede ayudar a agilizar la velocidad de desarrollo. Sin embargo para un entorno de desarrollo profesional es útil tener diferentes formas de referencias versiones anteriores de nuestras funciones. Este es el propósito de utilizar Versiones y Alias.

Si todavía no has trabajado con funciones Lambda, te recomiendo leer estos artículos para empezar:

Versiones

Las versiones cómo su nombre lo indica, guardan diferentes versiones publicadas de tu función Lambda.

Al publicar una versión, AWS crea una copia del estado actual de nuestra función y le asigna un número. De esta manera podemos seguir trabajando sobre nuevos cambios que se necesiten en la Lambda, pero guardar una versión funcional de la misma.

Es importante también que tengas en cuenta que no puedes modificar una versión. Se pueden cambiar algunas cosas como los permisos, pero no puedes cambiar cosas como el código o las variables de entorno. Si por ejemplo ya vas en la versión 5 pero necesitas regresar a la 4 y hacerle modificaciones, tendrás que copiar la funcionalidad de dicha versión y publicar la versión 6.

Alias

Un Alias es simplemente una versión Lambda con un nombre específico. Por esto mismo un Alias no puede existir sin que le hayas asignado una versión.

A primera vista puede ser que no logres discernir un caso de uso específico para un Alias. Al fin y al cabo las Versiones tienen un campo de descripción que bien podría funcionar para identificar cada versión.


Veamos un caso de uso en el qué veamos los pros y los contras de utilizar una función lambda directamente, una versión o un alias con un servicio

Caso de uso

Supongamos qué estamos trabajando en un proyecto de ranking de películas. Es un proyecto grande con el trabajo de back-end y front-end dividido entre diferentes equipos pertenecientes a diferentes compañias. El equipo del API fue el primero en empezar a trabajar en el proyecto y posteriormente se incorporaron el equipo encargado del front-end de una app web y un equipo de desarrollo móvil.

Para este ejemplo supongamos que tenemos un API ya listo. (En este ejemplo el API solo esta compuesto de 1 método).

Nota: Si quieres seguir los ejemplos en este caso de uso, necesitarás tener una comprensión básica de API Gateway. Para ello te recomiendo estos posts:

Captura de pantalla mostrando la configuración de la sección de la "Solicitud de Integración" del método GET. La función lambda que usa el método es la función movieDetails.

El método GET de /movie manda a llamar a nuestra función lambda movieDetails.

Captura de pantalla mostrando un API llamado SampleAPI con un recurso llamado movie y un método GET.

Para simplificar el ejemplo, la función movieDetails devuelve una respuesta estática:

exports.movieDetails = async (event, context, callback) => {

    return {
        "id": 1,
        "title": "007: No Time to Die",
        "actors": [
            "Daniel Craig",
            "Rami Malek",
            "Léa Seydoux",
            "Lashana Lynch"
        ],
        "franchiseFilms": [
            "007: Casino Royale",
            "007: Quantom of Solace",
            "007: Skyfall",
            "007: Spectrum"
        ],
        "releaseDate": "28 September 2021"
    }
}

Por ende al llamar al API, esa ruta nos devuelve el siguiente resultado:

Captura de pantalla mostrando una petición exitosa a la URL del API. La respuesta es exitosa y regresa el objeto del código anterior con un código 200.

Sin embargo como en todo proyecto, llega un nuevo requerimiento. Debemos actualizar el modelo de respuesta para que pueda mostrar nueva información.

Para ello tenemos que actualizar a este formato:

exports.movieDetails = async (event, context, callback) => {

    return {
        "id": 1,
        "title": "007: No Time to Die",
        "cast": [
            "Daniel Craig",
            "Rami Malek",
            "Léa Seydoux",
            "Lashana Lynch"
        ],
        "franchiseFilms": [
            {
                "id": 12,
                "title": "007: Casino Royale",
            },
            {
                "id": 18,
                "title": "007: Quantom of Solace",
            },
            {
                "id": 19,
                "title": "007: Skyfall",
            },
            {
                "id": 11,
                "title": "007: Spectrum"
            }
        ],
        "releaseDate": "28 September 2021"
    }
}

No es un requerimiento difícil pero lamentablemente dependiendo de si tu API esta usando lambdas directamente, con versiones o con aliases, algunos de estos cambios tendrán diferentes implicaciones. Veamos los 3 escenarios que podrían ocurrir en cada caso.


Escenario A – Uso de funciones Lambda directamente

Diagrama mostrando que un desarrollador hace cambios que afectan directamente al API y a la función lambda: movieDetails. Las apps tienen acceso a la ruta que ejecuta la misma función lambda.

Este es el escenario que potencialmente puede ocasionar más problemas para otros equipos. ¿Por qué?

Tú como desarrollador estás trabajando tanto en las rutas del API como en las funciones Lambda que interactuan con el mismo.

Al hacer los cambios necesarios en la función movieDetails, el código que este consumiendo el API ya no encontrará la propiedad de actors que existía previamente. A su vez, quienes estén esperando un arreglo de strings en la propiedad franchiseFilms tendrán un error porque ahora es un arreglo de objetos. Los cambios afectarán inmediatamente a quienes esten utilizando el API desde el momento en el que guardes los cambios. Esto incluye cualquier error que suceda mientras estes programando.

No hace falta decir que es mejor evitar este escenario ya que terminará afectando los tiempos de desarrollo de los demás equipos.

Escenario B – Uso de Versiones Lambda

Diagrama mostrando que un desarrollador hace cambios que afectan directamente al API y a la función lambda: movieDetails. Las apps tienen acceso a la ruta que ejecuta una versión predefinda de la función lambda.

Este escenario ayuda a prevenir los incidentes del escenario A. La razón es simple, si un API esta apuntando a una versión específica de la función en lugar de a la lambda directamente, los cambios que hagas como desarrollador no afectarán al API inmediatamente.

Para empezar a utilizar versiones simplemente basta con ir a la tab de Versiones de tu función Lambda.

Captura de pantalla mostrando la pestaña de Versiones sin ninguna versión disponible dentro del panel de la función lambda: movieDetails.

A continuación añade una descripción para poder identificar la versión con facilidad.

Captura de pantalla mostrandola ventana 
 de "Publicar una versión" con una descripción incial "Versión inicial".

AWS mostrará que tu versión se ha creado con éxito y ahora la verás listada en la tab de Versiones.

Captura de pantalla mostrando la pestaña de Versiones con la versión recién creada en el listado.

Nota: AWS guarda un historial del número de versiones que se han creado para la función. En mi caso ya había trabajado con versiones para esta función y por eso AWS me creo la versión 5. Sin embargo el número que AWS asigne a tu versión es irrelevante, la lógica es la misma.


Una vez terminado este paso falta hacer que el método GET /movie llamé a esta versión de tu lambda. Para ello solo hay que cambiar la función Lambda dentro de la sección de Solicitud de Integración de tu método.

Captura de pantalla mostrando la asignación de la función Lambda movieDetails 5, dentro de la configuración de Solicitud de Integración del método GET del recurso movie.

Como puedes ver solo basta con agregarle el sufijo de la versión que quieres. En mi caso es la 5, pero tu puedes agregar el número que necesites.

Finalmente solo necesitas crear una nueva implementación del API para ver reflejados los cambios.


Esto sería lo necesario para proteger la versión de la función sobre la que estan trabajando los demás equipos.

Ahora si puedes trabajar en la nueva funcionalidad sin preocuparte de más.

Captura de pantalla mostrando el editor de código  dentro del panel de la función Lambda.

Una vez hayas terminado tendrás que hacer el mismo procedimiento:

  1. Publicar una nueva versión.
  2. Actualizar la versión en el API.
Captura de pantalla mostrando la configuración de la nueva versión creada de la función Lambda. La versión 6.
Captura de panatalla mostrando la actualización de la función lambda a laa que apunta elmétodo GET del recurso movie. La nueva función es movieDetails 6.

Ahora al llamar al servicio del API, se muestra la siguiente respuesta.

Captura de pantallamostrando una llamada a la URL del API con una respuesta exitosa.

¡Perfecto! Con esto se puede trabajar en cambios sin afectar a otros equipos de desarrollo. No solo eso sino que además en caso de que quieras reutilizar alguna versión anterior solo basta con actualizar la llamada en el API.

Ahora… ¿tiene algun problema hacer esto? Para los otros equipos no, pero para ti si. Hacer este cambio para una sola función Lambda es extremadamente fácil y rápido. Pero…¿qué pasa si hay que modificar muchas rutas y lambdas a la vez? Multiplica este proceso que acabamos de hacer por 10 o más veces. No es imposible pero es muy laborioso. Hay una forma más eficaz para ti como desarrollador del API de hacerlo.

Escenario C – Uso de Lambda Alias

Diagrama mostrando que un desarrollador hace cambios que afectan directamente al API y a la función lambda: movieDetails. Las apps tienen acceso a la ruta que ejecuta un alias predefindo de la función lambda. El alias a su vez apunta a una de las versiones de la función lambda.

Los Alias no son otra cosa que nombres de una función Lambda que apunta a una versión específica. ¿Cómo puede ayudar esto?

Bueno al apuntar nuestro método a un Alias en lugar de la versión efectivamente estamos haciendo que el Alias sea el que tenga el control de las versiones en lugar de nuestro API. Esto quiere decir que en lugar de cambiar la versión a la que apunta el API como lo hicimos en el escenario B ahora solo tendríamso que cambiar la versión a la que apunta el Alias.

Para empezar a trabajar con un Alias necesitas tener al menos una versión publicada. Una vez hecho esto procede a la tab de Alias de tu función Lambda.

Captura de pantalla mostrando el listado vacío de la pestaña Alias de la función movieDetails.

Al crear el Alias el formulario te pide seleccionar una nombre, descripción y versión.

En mi caso lo llene de la siguiente manera:

  • Nombre: movieDetails-API
  • Descripción: Alias creado para el API
  • Versión: 5
Captura de pantalla mostrando el formulario al crear un alias, lleno con la información anterior.

Una vez creado el Alias puedes verlo listado en la tab de Alias.

Captura de pantalla mostrando la creación exitosa del alias: movieDetails-API
Captura de pantalla mostrando el nuevo alias: movieDetails-API, en el listado de la sección de Alias de la función movieDetails.

A su vez también puedes verlo en el listado de Versiones, ya que se mostrará que versión tiene un Alias asignado.

Captura de pantalla mostrando en el listado de versiones que la versión 5 esta asociada al alias: movieDetails-API

Nota: Si seguiste los pasos del escenario B, probablemente ya tengas 2 versiones en la lista. De no tenerlas puedes implementar algún cambio para publicar una nueva versión.


Por último hay que indicarle al API que utilicé el nuevo Alias. Para ello simplemente cambia la función Lambda dentro de la sección de Solicitud de Integración de tu método.

Al igual que con la versión, tienes que agregarle un sufijo al nombre de tu Lambda. El formato es <nombreLambda>:<nombreAlias>.


Ahora puedes intercambiar fácilmente entre las n versiones que hayas publicado de la Lambda.

Si quieres utilizar otra versión solo tienes que editar el Alias.

Captura de pantalla remarcando el botón de "Editar" en el panel de la pestaña de Alias de la función.

El API puede cambiar a usar el código de la primera versión.

Captura de pantalla mostrando una llamada exitosa a la URL del API. La respuesta contiene el objeto de la primera versión.

Y en cuestión de segundos puedes hacer que trabaje con el código de la nueva versión.

Captura de pantalla mostrando una llamada exitosa a la URL del API. La respuesta contiene el objeto de la segunda versión.

Nota: Recuerda que si bien el ejemplo se enfoca en el uso de un API, esto aplica para cualquier servicio que utilicé una Lambda como EventBridge, SNS, etc.


¡Listo!

Ahora sabes como utilizar Versiones y Aliases con tus Lambdas y mejor aún, sabes como sacarles mayor provecho.