Web

Serverless autrement : faire du web

by Antonin Savoie 13 juin 2019

L’on entend souvent parler des nouveaux frameworks Web, de leur évolutions. Certains font le buzz, d’autres disparaissent, de manière sporadique. Et il en va de même pour les architectures applicatives, qui ont droit à leurs lots d’évolutions et d’innovations.

Il y a encore peu de temps, l’architecture monolithique, où tout est installé sur un seul serveur, était LA solution à adopter. Puis nous avons pu découvrir l’approche microservices, où une application peut être découpée et déployée sur différents serveurs. Plus récemment, avec l’émergence de Docker, la conteneurisation a eu le vent en poupe. 

Dernièrement, c’est l’architecture Serverless qui fait parler d’elle.

Serverless

Serverless décrivait dans un premier temps les applications qui utilisaient exclusivement (ou presque) des services tiers hébergés dans le cloud afin de gérer la logique backend : l’authentification, les récupérations de contenus, etc.. Cette approche était beaucoup utilisée dans le cas d’applications web dites “riches”, qui embarquent de fait de la logique métier dans la couche frontend.

Mais Serverless décrit également une application dans laquelle le code métier backend n’est plus exécuté sur un seul serveur, mais dans plein de mini conteneurs qui sont démarrés à la demande, uniquement quand cela est utile. Cette approche est souvent appelée “Function as a Service” (Faas). Un des services cloud exposant ce principe le plus connu est “AWS Lambda”.

Au delà de cette approche FaaS, il existe de nombreux concepts et services cloud qui peuvent rentrer dans la case “Serverless”. Il existe pléthore d’articles décrivant des systèmes et des approches différentes. Dans cet article, nous allons nous concentrer sur cette approche FaaS, pour faire du web “classique”, sans forcément décrire une application riche.

Je ne vais pas rentrer plus dans le détail de ce que peut être Serverless, mais je vous conseille le très bon article  de Martin Fowler si vous souhaitez en savoir plus.

Souvent, les architectures Serverless avec des FaaS sont présentées comme une solution efficace pour créer des applications riches, où chaque Lambda est un endpoint API, et la logique métier est partagée entre le backend et le client front (le plus souvent un framework Javascript).

Mais l’on peut également utiliser des architectures Serverless pour faire des sites plus simples, plus “classiques”, où la logique métier est concentrée côté backend. C’est ce que je vous propose de voir dans cet article.

Serverless sur AWS

Dans notre exemple, nous allons travailler avec le fournisseur de service cloud d’Amazon : AWS. Je ne sais pas si c’est le plus performant, le moins cher, le meilleur, mais c’est en tout cas celui que je connais, et qui est parmi les plus connus.

Nous allons utiliser principalement deux services : AWS Lambda et Api Gateway.

AWS Lambda est un service de fonction cloud. Sommairement, du code est associé à un mini conteneur, qui, lorsqu’il est déclenché, s’allume, exécute son code, et renvoie une réponse adaptée au déclencheur. C’est dans ces Lambdas que nous allons mettre notre code métier.

Le deuxième service, Api Gateway, permet de créer des endpoints API, que l’on va venir brancher sur nos Lambdas. Ce sera le déclencheur de nos Lambdas, et notre point d’entrée vers notre site, qui portera nos urls.

Pour combiner facilement ces deux services, nous allons utiliser Serverless Framework, qui nous permet de décrire notre infrastructure avec du code, et de déployer facilement nos Lambdas et leurs événements.

Exemple : site de recettes de cuisine

Prenons pour cet article un cas simple : un site de recettes affichant une homepage avec les 3 dernières recettes publiées et une page affichant le détail d’une recette.

L’approche classique serait de créer une application côté client, en Vue.js ou React par exemple, de créer une API, qui est consommée par notre application.

Mais on peut aussi avoir l’approche inverse : créer des endpoints API, et s’en servir comme des urls de sites classiques : nos lambdas retournent le HTML du site directement, et non pas des données consommées par une application riche en front.

Voyons voir comment l’on peut mettre cela en place. C’est parti !

Commençons par découper notre application.

Nous avons besoin de 2 urls :

  • mes-recettes.fr/ : notre homepage
  • mes-recettes.fr/crecette/{ID} : l’affichage d’une recette

Nous aurons donc 2 Lambdas : une qui va rendre le HTML de la homepage, une qui va rendre le HTML d’un contenu complet. Sur chacun de ces Lambdas sera branché un déclencheur Api Gateway, correspondant à une url.

Les données maintenant. On pourrait utiliser un CMS headless, ou stocker nos données dans une base DynamoDB, mais pour la simplicité de cet exemple, nous allons juste consommer un fichier JSON local embarqué dans nos Lambdas.

Voici à quoi ressemble une recette :

Définir et créer nos Lambdas

Une fois la stack serverless initialisée grâce à Serverless Framework, nous pouvons définir nos deux fonctions, ainsi que leurs déclencheurs.

Nous avons ici défini nos 2 Lambdas, avec les événements HTTP associés, ainsi que leurs urls.

Code métier

Mettons-nous d’accord, dans notre cas, la partie “code métier” est très limitée. Elle est composée d’un fichier qui va répondre aux événements HTTP, qui va récupérer les données voulues, générer le HTML associé, et renvoyer le tout.

Pour accompagner cette partie, nous avons un service qui viendra nous fournir la donnée (ici, une simple lecture JSON), ainsi qu’un service exposant la librairie Nunjucks, qui est un moteur de template inspiré de Twig pour Node.js.

Générer du HTML

Avec l’aide de Nunjucks, il est très simple de générer du HTML avec Node.js, en se rapprochant des paradigmes de twig : conditions, boucles, heritages, etc… Il est même possible de définir des filtres et fonctions custom.

Afin de rester simple, j’ai utilisé materialize.css pour le style.

Voici le résultat :

Le template de la homepage :

Le template du détail d’une recette :

Le template parent :

Le déploiement !

Une fois ces différents services mis en place, il ne nous reste plus qu’à déployer notre site !

Rien de plus simple grâce à Serverless Framework :

serverless deploy

Automatiquement, le framework va créer nos Lambdas, créer les entrées Api Gateway, et nous donner les informations de notre site : nos urls !

https://2ca3swlmo3.execute-api.eu-west-1.amazonaws.com/dev/

https://2ca3swlmo3.execute-api.eu-west-1.amazonaws.com/dev/recipe/1687

Ces urls ne sont pas “belles”, car ce sont les urls directs vers Api Gateway, mais rien ne nous empêche de faire pointer un vrai nom de domaine dessus si besoin (à l’aide de Route53 par exemple).

Pourquoi utiliser cette approche

De prime abord, cette approche peut ne pas être avantageuse par rapport à un site construit de manière un peu plus classique, avec Symfony, Express, ou autre approche du même genre. Mais elle possède tout de même quelques avantages :

  • Une économie de coût : l’approche Serverless permet d’utiliser les ressources uniquement quand il y en a besoin, et le prix des Lambdas sur AWS est très bas.
  • Une scalabilité « out of the box » : si nos Lambdas sont trop sollicitées, AWS va automatiquement en  provisionner plus.
  • Une création d’environnement simple : déployer un nouvel environnement de test ou de production se fait en changeant le paramètre « stage » de notre configuration.
  • Un « time to launch » réduit : pas d’installation de serveur, pas de conflit de configuration : le déploiement se fait en quelques minutes, grâce à une commande.
  • Une intégration directe dans l’écosystème AWS : il est maintenant très facile d’utiliser d’autres services proposés par AWS, sans souci de droit ou de sécurité.
  • Un développement facile : grâce par exemple au plugin https://www.npmjs.com/package/serverless-offline il est rapide de mettre en place un environnement de développement en local pour travailler sur les Lambdas avant des les déployer.
  • Un déploiement rapide : en effet, une commande pour déployer tout notre site, qui prend quelques minutes à peine.
  • Une automatisation évidente : il est très facile d’automatiser le déploiement d’une stack Serverless, et d’inclure ce déploiement au sein d’une chaîne plus complète (tests automatiques, Terraform, etc..).
  • Une transition vers des microservices naturels : définir une stack par service serait logique, et permet de compartimenter facilement plusieurs parties de l’application.
  • Une mixité de langage aisé : on peut combiner des Lambdas écrites dans plusieurs langages sans problème.

 

Que d’avantages ! Attention cependant, il peut y avoir quelques inconvénients :

  • Le temps de démarrage des Lambdas peut être pénalisant. Il existe des solutions et des stratégies de « warm up« , mais cela aura un petit impact sur le coût global.
  • Le temps d’apprentissage des services AWS/Cloud peut être un peu long.
  • Un changement de mentalité : plutôt que d’installer des services sur un serveur, il faut se tourner vers les services proposés par les fournisseurs pour répondre à nos besoins.
  • Tout le code d’une stack est déployé sur toutes nos Lambdas : pratique pour le partage de fichiers et de ressources, mais plus ce package va grossir, plus le temps de déploiement peut s’avérer long.

 

En résumé, l’approche Serverless permet d’accélérer le début d’un projet, de s’intégrer très simplement dans un écosystème cloud, mais quelques paramètres restent à surveiller.

Vous pouvez retrouver le code de l’exemple sur Github.

Webinar

Projet mobile avec React Native : les 5 erreurs à éviter

S'inscrire au webinar

Vous avez un projet ? Nos équipes répondent à vos questions

Contactez-nous