Utiliser AWS pour déployer un projet d’une startup: Partie 1 - Frontend
Le défi
Il y a quelques années, j’ai rejoint une startup pour créer un produit qui voulait trouver sa place sur le marché.
D’abord, j’ai rejoint l’équipe en tant que développeur Frontend et, après avoir terminé la première version de l’application, je voulais m’impliquer davantage côté backend. Alors, j’ai échangé mon rôle avec le développeur Backend.
L’application était composée de trois services : une API Backend, un Frontend que nous voulions aussi déployer sur les appareils mobiles, et un panneau d’administration.
Avec le CTO, nous avons décidé que nous pouvions déployer nos services sur AWS, et que nous utiliserions des images Docker. Par conséquent, nous avons choisi AWS ECS comme notre plateforme de déploiement.
Nous n’avons pas choisi Kubernetes, car nous n’avions pas beaucoup d’utilisateurs au début.
Par ailleurs, nous avions des besoins spécifiques:
Frontend: Devrait être stocké dans le côté utilisateur (client-side), et l’utilisateur doit être capable de télécharger une photo.
API Backend: Devrait être publique, pour être consommée par l’application mobile et le Frontend.
Admin: Devrait être un outil d’utilisation interne. Du fait que nous étions une petite startup à ce temps-là, il était logique d’utiliser les connexions VPN.
Pour tous les cas précédents, nous avions besoin d’un environnement de test, que nous avons nommé l’environnement staging.
Pour les prochains exemples, je vais utiliser thestartup.domain
(lastartup.domaine en français) comme un domaine d’exemple. Les exemples peuvent varier du diagramme et des cas réels, car c’est un concept général basé sur ma mémoire.
Pourquoi ne pas utiliser la console d’AWS, et pourquoi nous utilisons Terraform?
Du coup, nous avions expérimenté en créant les raccourcis manuellement dans la console, mais nous avons vu que dépendre de la mémoire pour commencer à faire les modifications peut être dangereux, et que nous pourrions endommager les ressources accidentellement.
Bien que nous ayons eu accès à CloudFormation, je ne me souviens pas des caractéristiques que nous avons mises à ce temps-là. Alors, nous avons choisi Terraform à la place de CloudFormation. Je me rappelle que la raison principale était la syntaxe plus claire et facile comparée à CloudFormation.
Frontend
L’architecture
Pour le frontend, nous avons fait des recherches pour utiliser S3 pour héberger notre application statique. Nous pourrions utiliser CloudFront connecté à AWS Certificate Manager pour déployer une application complète statique HTTPS pour servir HTML. Aussi, CloudFront héberge en cache le contenu dans ses Edges. Ça fait du sens, comme l’option la plus logique.
Deux zones de disponibilité différentes
Nous utilisions deux zones de disponibilité différentes, car utiliser us-east-1
est risqué, tous les nouveaux changements d’AWS seront déployés là, et ils peuvent causer des disruptions dans la plateforme.
Le seul service que nous ne pouvions pas déplacer était l’Administrateur des certificats. Pour valider notre domaine, il devait être dans us-east-1
.
Nous utilisons deux domaines
La raison pour laquelle nous avions utilisé deux domaines pour déployer l’application, hors de thestartup.domain était parce que la page principale était une page landing, et nous voulions déployer l’application réelle dans un sous-domaine. Comme j’ai écrit, nous voulions avoir un environnement staging que chaque développeur peut utiliser.
Héberger les environnements de production et staging dans un seul bucket
Bien sûr, nous pouvons créer un bucket par projet. Mais avec Terraform, pour reproduire un environnement par développeur, nous avions utilisé un seul bucket avec des dossiers différents. Créer un bucket par dossier ressemblait à du sur-engineering pour l’architecture.
Utiliser CloudFront pour montrer le contenu du bucket
Pour profiter du cache et éviter de l’exposer, nous avons créé deux distributions CloudFront sur la couche de prix la moins chère : PriceClass_100
. Avec ça, nous serons certains que notre contenu restera seulement dans le cache pour le public d’Amérique (nord et sud).
Certificat
Notre certificat était de type wildcard. C’est juste au cas où nous voudrions plus d’alternatives ou d’instances de test pour le frontend. Un certificat de type wildcard permet d’attribuer de multiples sous-domaines à un seul certificat.
Pour ce cas, nous avons utilisé *.frontend.thestartup.domain
.
Un environnement par développeur
Pour deux semaines, nous avons essayé avec l’URL comme developpeurun.frontend.thestartup.domain
. Mais, nous n’avions pas le temps de renforcer certaines politiques au moment de faire un merge dans nos branches de Git, il était dur de tenir le code comme ça. L’idée était d’avoir deux environnements alternatifs visant la même API de staging.
Même si nous avons recréé la même structure sur Terraform par Pull Request, ça peut prendre beaucoup de temps pour attendre le déploiement, nous avons laissé tomber l’idée.
Le flux pour déployer le projet (Pipeline)
Le flux était pour construire le HTML et le déployer comme du contenu statique. Pour éviter de sortir de l’écosystème AWS, j’ai utilisé AWS CodeCommit combiné avec AWS CodeBuild pour la première version.
Mais les Github Actions ont commencé à gagner en popularité à ce temps-là, donc, nous avons décidé de faire la migration vers Github Actions, car nous pouvions créer des rapports par Pull Request.
Alors, dans le bucket nous avions deux répertoires : l’un appelé /production
et l’autre /staging
. Après la construction de chaque projet, nous avons changé les variables d’environnement pour viser l’API de staging aussi.
Flux en Github
Ceci est un script similaire à celui que nous avons utilisé pour déployer le code.
DOMAIN_NAME
(nom de domaine) a été changé parmi les environnements. Nous avions l’habitude de détecter la distribution de CloudFront à viser pour invalider le cache quand nous avions fini avec le déploiement dans le bucket.
Qu’est-ce que je peux améliorer actuellement?
Le code que tu as révisé ces dernières années te fait te sentir embarrassé ? C’est complètement normal ! Nous, comme développeurs, quand nous avons plus de connaissances, nous verrons les échecs du passé et nous réfléchirons aux manières dont nous pouvons les éviter. C’est pourquoi j’ai créé une liste d’améliorations si je dois créer le même environnement actuellement.
Ajouter WAF
Car la sécurité est très importante maintenant, ajouter WAF serait obligatoire pour moi. AWS WAF ajoute une protection contre les injections SQL et le cross-site scripting (XSS). Aussi, il ajoute une couche de protection contre les bots. Dans le monde actuel, les bots continueront l’utilisation de ton site de manière répétée, en cherchant quelque vulnérabilité, ou ils peuvent « lire » ton site, en consommant des ressources et de la mémoire.
Utiliser un bucket différent par projet
Pour des objectifs de sécurité, j’ai essayé de mettre tous les contenus de déploiement dans le même bucket. Donc, une fois que je dois donner des accès à chaque développeur, ça va être simple, parce qu’il faut gérer une seule ressource.
Mon but sera de créer des buckets séparés pour chaque environnement, nous permettant de gérer chaque permission de développeur individuellement par ressource et de restreindre l’accès au bucket de production au personnel autorisé dans la compagnie.
Si nous avons besoin d’un environnement différent par développeur
Si nous avons besoin d’avoir plus d’environnements hors de staging ou production, je vais préférer déployer ces environnements temporels dans un conteneur NGINX qui servira le contenu comme un serveur web, car attendre pour la création d’une distribution CloudFront peut être cher en termes d’argent et de temps.
Sur la prochaine partie
La partie 2 couvrira le backend, dont la complexité la plus grande reste. Parce que nous avions à déployer les conteneurs, AWS ECS nous a aidé à réduire la maintenance de nos conteneurs.
Je vais faire une mise à jour au post dans la section des recommandés quand l’autre post sera prêt.