adding tuto

This commit is contained in:
theo1 2020-12-18 19:40:25 +01:00
parent 4938c90743
commit 27d0b8e023

210
interneeeet.md Normal file
View File

@ -0,0 +1,210 @@
[toc]
Tout d'abord, il faut savoir un truc : la structure d'Internet n'a pas changé depuis le début. Tout fonctionne _globalement_ pareil, et comprendre le rôle de chacune des parties qui la compose permet de comprendre comment fonctionne n'importe quel site web.
## Première partie : les morceaux
On va commencer par ça : les différentes parties qui composent ce qu'on appelle Internet (ou plus précisément le **web**, c'est-à-dire la partie d'Internet qui est visible pour nous). C'est des mots qui vont paraître familiers, et c'est normal, on les utilise tous les jours.
* D'un côté, il y a les **navigateurs** (_browsers_ en anglais). Leur rôle est très simple : c'est d'afficher des pages HTML. Le HTML, c'est du texte, rien de plus. C'est du texte, écrit d'une telle manière qu'une machine sait quelles parties correspondent aux titres, au contenu, aux images, etc. Mais c'est du texte. D'où cette BD d'XKCD, qui blague sur le fait qu'au final les navigateurs ne font rien de bien compliqué.
![Perspective](https://imgs.xkcd.com/comics/perspective.png)
* D'un autre côté, on a les **serveurs**. Les serveurs, c'est des machines sur lesquels tournent des programmes, qui répondent aux navigateurs qui leurs demandent des pages HTML en leur envoyant...bah des pages HTML. Un prof m'a dit un jour un truc qui m'a aidé : le serveur le plus simple, c'est un `while (true)`, et rien d'autre. Dans ce `while (true)`, il y a 1. une oreille qui écoute les requêtes des navigateurs, 2. des fonctions qui déterminent quel fichier HTML envoyer, et 3. des fonctions qui renvoient ces pages sur le réseau.
* Entre les deux, on a **Internet**, c'est-à-dire les tuyaux qui permettent d'acheminer les requêtes entre les navigateurs et les serveurs, et les réponses contenant les fichiers HTML entre les serveurs et les navigateurs.
Et voilà, avec un navigateur d'un côté, un serveur de l'autre, des tuyaux entre les deux, et des fichiers HTML à partager, on a des sites web.
Et on a aussi une première version du web, ce qu'en rétrospective on a appelé le **web 1.0** : c'est les sites moches qu'on peut encore voir parfois, qui ne font pas grand chose, mais peuvent répondre à des besoins simples comme réaliser un blog, centraliser des informations pour une mairie de village...
## Deuxième étape : les sites dynamiques
Ensuite viennent les années 90, et assez vite on réalise qu'avec ce qu'il y a dessus, on est très limité : _la même chose sera affichée pour tout le monde sur le site, quoi qu'il arrive_. Pourquoi c'est un problème ?
Eh bien, c'est comme si à la place d'un guichet d'accueil avec une vraie personne pour s'occuper de nos problèmes dans une gare, il y avait un présentoir avec un livret d'information. Le livret peut être très complet sur tout ce qu'il faut savoir sur la gare, il peut être très joli et rendre l'information la plus accessible et lisible possible par le plus de gens, mais il y aura tout de même un paquet de chose qu'il ne pourra pas faire : vendre et échanger des billets, vous rembourser si besoin, garder en mémoire vos derniers déplacements...
Sur Internet, il faut par exemple imaginer que le concept de compte sur un site ne peut pas exister avec de simples pages HTML pré-écrites et accessibles sur un serveur : le site réagira exactement de la même manière si on lui dit "Je suis theo" ou "Je suis Jean-Michel Jare".
Et là, les gens d'internet, après s'être gratté le menton un moment, se disent : « On a qu'à écrire un programme qui garde en mémoire les informations de tous les utilsateur⋅ices, et qui écrit des pages HTML différentes pour tout le monde en fonction de ces informations. » Décortiquons.
Ce programme, c'est **un serveur**, c'est-à-dire comme vu ci-dessus, des programmes qui renvoient des pages HTML pour les envoyer aux navigateurs. Sauf que là, plutôt que de juste bêtement renvoyer des fichiers déjà écrits sur le serveur, le programme va lui-même construire une page HTML avant de l'envoyer au navigateur qui lui a demandé. Par exemple, il va voir que l'adresse IP `192.168.0.1` lui a demandé le fichier `monip.html`, et il va écrire dans ce fichier `Bonjour. Votre IP est :192.168.0.1`. Et voilà, on a construit (presque) le site [whatismyip.com](https://www.whatismyip.com/fr/).
Bon, on imagine que pour faire des vrais sites utiles, il va falloir aller un peu plus loin. En fait, c'est des véritables **applications** qui vont se construire. Elles sont écrites dans différents **langages de programmation**, comme le PHP ou Java, mais aussi plus récemment Python, Elixir, Go, Rust, C, C++, Haskell, Clojure... y'en a un paquet.
Chacun de ses langages a des **librairies** (ou modules) qui permettent d'éviter de réécrire les même choses tout le temps, et même des **frameworks**, qui permettent de rapidement faire des projets qui ont la même structure. Par exemple, ces librairies peuvent :
* authentifier un⋅e utilisateur⋅ice : si celui-ci envoi un certain nom d'utilisateur⋅ice accompagné d'un certain mot de passe, alors lui permettre d'accéder à des pages HTML qui contiennent des informations personnelles.
* interagir avec une base de données pour stocker ces informations.
* communiquer avec une banque pour valider une demande de paiement.
* ...
Quelques exemples de framework pour la culture générale : Symfony et Laravel en PHP, Django en Python, Phoenix en Elixir...
Bravo, ton site est maintenant **dynamique**, il permet de faire un paquet de chose.
## Deuxième étape bis : ce qu'il se passe dans le navigateur.
Donc on sait faire des sites qui interagissent différemment selon les information qu'on lui demande. Pendant ce temps, une autre chose a évolué depuis les années 80 et les débuts d'Internet : c'est ce qu'il se passe dans le navigateur.
Avoir un paquet de pages HTML qui s'affichent sur un navigateur, c'est super, et on peut tout faire avec ça.
Mais on réalise vite que les serveurs sont **surchargés** : on est au début des années 2000, de plus en plus de gens utilisent les sites Internet, et à moins d'avoir des serveurs très efficaces fonctionnant sur des machines très puissantes, les programmes peuvent mettre un paquet de temps à répondre. Et ce n'est pas toujours très malin.
Imaginons que je sois devant un formulaire qui me demande de rentrer mon numéro de téléphone portable pour qu'on me recontacte. J'oublie un numéro, mais je ne m'en rend pas compte. J'envoie le formulaire, le serveur vérifie les informations et se rend compte que le numéro n'a pas un format valide. Il me renvoie une page HTML comportant une erreur, et je n'ai plus qu'à recommencer. Et j'ai utilisé le temps de serveur pendant quelques millisecondes, ce qui aurait permis de répondre à quelqu'un d'autre, avec des informations utiles cette fois.
C'est trop bête. Et si le navigateur pouvait lui-même vérifier le format du numéro de téléphone et m'avertir avant que je clique sur "Envoyer" que j'ai fais une erreur ... et c'est exactement ce qu'on va faire, au moyen d'un nouvel élément : **Javascript**.
Javascript, un langage de programmation, mais qui a une particularité : on peut envoyer un fichier Javascript à un navigateur, et celui-ci va **lexécuter**. C'est une spécificité de ce langage : dès que le navigateur va recevoir ce programme, il va le passer dans un **interpréteur**, qui va exécuter dérouler toutes les instructions du programme. Ces instructions peuvent être par exemple :
* lire un texte entré par un utilisateur dans une case.
* vérifier qu'il y a bien 10 numéros dans telle entrée
* si ce n'est pas le cas, afficher le message suivant : « Attention à ce qui tu écris, boloss ».
Donc ce langage, pas très utile au début - mon père m'a encore dit récemment que pour lui Javascript servait surtout à faire des petites animations - va être de plus en plus utilisé, afin de **décharger les serveurs** de tâches qui peuvent être effectuées dans le navigateur (on dit aussi "côté client"). Pour une page HTML qui contient un formulaire, il vaudra mieux écrire un petit programme Javascript qui permet d'effectuer les vérifications nécessaires dans le navigateur, plutôt que de devoir se taper tout côté serveur. En plus, ça évitera que les pages se rechargent toutes les deux secondes sous nos yeux, ce qui casse à chaque fois la navigation sur un site.
Et tout comme pour les langages de serveur, il va y avoir des **modules** Javascript, qui vont permettre de faire rapidement des choses récurrentes. Le module - ou librairie - le plus connu est sans doute **jQuery**, qui est un espèce de gros paquet de code (jusqu'à [249.58 KB](https://mathiasbynens.be/demo/jquery-size) pour la dernière version : ça peut sembler pas énorme, mais il faut garder en tête que c'est envoyé avec _chaque page utilisateur⋅ice_, donc pour un site avec ne serait-ce que quelques dizaines d'utilisateur⋅ices en permanence, ça peut vite faire beaucoup).
Ensuite il y a eu des **framework** Javascript, qui ont permis de rapidement faire des projets structurés de la même manière... on en parle juste après.
## Troisième partie : « c'est trop lourd votre truc »
### Les SPA
Ce qu'il faut comprendre, c'est que :
1. les serveurs tirent la langue : les sites fortement utilisés doivent faire face à un grand paquet de requête, et construire des pages HTML à chaque fois demande beaucoup de boulot
2. on sait faire de plus en plus de chose dans les navigateurs.
Tiens tiens mais... et si on faisait faire une partie du boulot aux navigateurs du coup ?
Et c'est ce qu'on va faire à partir des années 2010, et c'est ce qu'on appelle les **Single Page Applications** (SPA), et c'est la manière "moderne" de faire des sites complexes en 2020.
L'idée est la suivante : on essaye au maximum de limiter les requêtes faites d'un navigateur au serveur, et quand on en fait on essaye de demander le moins de calcul possible. Alors on va imaginer une chose assez marrante : on va en fait envoyer **un seul fichier HTML** au client lors de sa première requête. Sauf qu'avec ce fichier, on va envoyer un gros, gros paquet de fichiers Javascript, qui vont se charger de **construire le HTML une fois exécutés dans le navigateur**. On renverse la structure expliquée dans l'étape n°2, où c'est le serveur qui va construire le HTML. Là, c'est le code qui va le construire (toujours), mais côté navigateur. C'est ce qu'on appelle le **rendering**.
Quel intérêt ? Eh bien, par exemple, si je veux passer de la page "À propos" à la page "Contact", plutôt que de demander au serveur de me l'envoyer, un code Javascript va s'exécuter dans mon navigateur et remplacer le HTML que j'ai sous les yeux par le code de la nouvelle page. On vient d'économiser un aller-retour entre le navigateur et le serveur.
Bon, le serveur sert bien sûr toujours à quelque chose : c'est chez lui que sont les données. Par exemple, imaginons Facebook : l'application qu'on envoi à l'utilisateur⋅ice ne peut pas contenir tous les posts de tous les utilisateur⋅ices sur toutes les pages possibles. Au risque de dire l'évidence, ce n'est pas réaliste : ça représente des pétabytes de données, on ne va pas envoyer ça à une personne, sans parler d'à des centaines de millions. Qui plus est, ce n'est pas ce que l'ont veut faire : on veut envoyer à chaque utilisateur⋅ice les **les données dont iel a besoin**, et seulement celles qu'iel est autorisé⋅e à accéder.
En somme, une SPA, c'est un peu la structure du site, mais vidée de tout son contenu : c'est une timeline sans post, un profil sans photo ni information, etc. Une SPA sait _comment_ tout afficher, mais il faut qu'on lui dise _quoi_ afficher. Pour avoir ces données, on a toujours besoin d'un serveur.
Trois _frameworks_ Javascript sont aujourd'hui populaires pour développer des SPA : Angular, React et Vue, respectivement maintenus par Google, Facebook et une communauté à part.
### Les API
Et donc, comment une SPA va-t-elle obtenir ces informations auprès d'un serveur ?
Par différents moyens, il n'y a pas de règle unique. Mais très souvent, l'information va transiter via un format appelé JSON (Javascript Object Notation - attention ce format peut être utilisé par énormément de programmes qui n'ont rien à voir avec Javascript, il a simplement été développé pour Javascript _au début_ mais il est utilisé beaucoup plus largement aujourd'hui).
Voici un exemple d'information qui peut être envoyé par un serveur à une SPA au format JSON :
```json
{
"id" : 189555767
"name": "theo",
"nickname" : "theolem",
"friends" : [
"Manon",
"Mathurin",
"Félicie"
]
}
```
Ça devrait être assez clair : cet objet est envoyé à la SPA pour renseigner une page de profil.
Donc une SPA, c'est un site vide, qui va demander des informations au serveur pour remplir les trous. Et le mécanisme qui permet d'obtenir ces informations (au format JSON par exemple) s'appelle une API (Application Programming Interface). Il y a des dizaines de types d'API différentes, qui ont des fonctionnement et des qualités différentes, mais ce qu'il faut retenir c'est ça : **un serveur, pour fonctionner avec une SPA, doit implémenter une API**, c'est-à-dire fournir un mécanisme pour cette SPA puisse obtenir les informations dont elle a besoin.
Un exemple d'API simple peut être celui-ci :
* quand la SPA a besoin d'obtenir une liste de tous les utilisateur⋅icess du site, elle envoie une requête à `nomduserveur.ex/users`
* quand elle n'a besoin d'information que sur un⋅e utilisateur⋅ice, par exemple `max`, elle envoie une requête à `nomduserveur.ex/user/max.` Pour `lea`, ce sera `nomduserveur.ex/user/lea`, etc.
* quand elle a besoin d'obtenir des informations sur un événement qui a pour identifiant `1854885`, elle envoie une requête à `nomduserveur.ex/events/1854885`.
* ...
Sans trop s'attarder sur les API, il faut comprendre **l'évolution de structure d'un site web au fur et à mesure du temps** :
1. au début on avait un serveur qui répondait à _chaque requête_ en construisant le HTML à chaque fois qu'on lui demandait, ce qui demandait beaucoup de ressources
2. puis on a décidé que le navigateur devrait faire plus de boulot, et on lui a envoyé la totalité du site _d'un coup_, défini en code Javascript, et on laisse le navigateur aller chercher le contenu dont il a besoin.
L'avantage de ça, c'est avant tout que c'est beaucoup moins lourd pour le serveur : il fait simplement la passerelle intelligente entre la base de données et la SPA, avec bien sûr de l'intelligence dedans : il ne va pas envoyer d'informations sans vérifier que l'utilisateur⋅ice a bien le droit de les visualiser par exemple.
## Petits apartés marrants
### NodeJS : Javascript fait des siennes
Comme dit plus haut, Javascript a à la base été développé pour être exécuté dans un navigateur. Son but premier (et son unique objectif pendant des années) était de réagir aux actions des utilisateur⋅ices en modifiant le code HTML de la page au fur et à mesure de la navigation.
Mais il se trouve que le langage a évolué au fur et à mesure, et il peut à présent faire beaucoup plus de choses que ça : il peut faire des appels à des sites externes via `fetch`, stocker des variables de manière permanente...
Pendant très longtemps, Javascript n'a pas seulement été le **seul** langage exécuté dans le navigateur ([il n'est plus le seul à présent](https://developer.mozilla.org/fr/docs/WebAssembly)), il ne pouvait être exécuté **que** dans le navigateur. La raison pour ça était qu'on ne trouvait d'exécuteur de Javascript que dans le navigateur, donc impossible de l'exécuter en dehors, par exemple pour construire une application de bureau.
Puis un monsieur nommé [Ryan Dahl](https://en.wikipedia.org/wiki/Ryan_Dahl) (et un paquet d'autres gens l'ont aidé) a décidé qu'il n'y avait pas de raison, et que ce serait cool de pouvoir exécuter le Javascript n'importe où, comme on le fait avec des scripts Python par exemple. Alors il a simplement récupéré l'interpréteur Javascript de Chrome qui s'appelle V8, et il en a fait un environnement d'exécution en dehors du navigateur qu'il a appelé NodeJS. Ce qui fait que je peux à présent ouvrir un terminal, écrire un petit programme en Javascript dans un fichier et l'exécuter en lançant :
```bash
node monprogramme.js
```
Donc Javascript, c'est à présent un langage à part entière, qui peut s'exécuter sur n'importe quel système où Node est installé. Et la première chose qu'on a développé avec Node ça a été... des serveurs ! L'intérêt ? C'est que les développeur⋅euses web puissent écrire en un seul langage à la fois le _backend_ (le programme côté serveur qui renvoie du HTML) et le _frontend_ (les script JS qui viennent avec les pages HTML, ou les SPA par exemple).
Donc pas de panique : si on voit du Javascript partout à présent, c'est que ... il peut maintenant tout faire. (Attention, ça ne veut pas spécialement dire que c'est **le** langage à apprendre, simplement, ça existe).
### Les progressive web app (PWA)
Revenons une seconde sur les SPA : on remarque donc que le frontend s'autonomise de plus en plus, et ne doit contacter le backend que pour obtenir des données. En parallèle de ça, des sites basés sur des SPAs (comme l'excellent [Mobilizon](https://mobilizon.fr), par exemple) constituent une grosse partie de notre utilisation d'Internet chaque jour.
Alors plutôt que de laisser des onglets ouverts dans nos navigateurs, pourquoi ne pas permettre aux utilisateur⋅ices de sortir cette application dans un environnement qui aurait l'air d'une appli native ? C'est ce qu'on appelle une Progressive Web App, ou PWA. Celle-ci informe son client (navigateur) qu'elle est "installable", ce qui permet par exemple de créer une icône pour y accéder directement dans un environnement épuré :
![image-20201218175651509](/home/theo/.config/Typora/typora-user-images/image-20201218175651509.png)
_l'icône de la PWA de Mobilizon sur Ubuntu_
Une PWA sur mobile ressemblera finalement beaucoup à une application native, par exemple Android : simplement, elle ne demande pas d'effort d'installation, et le coût de développement est minime. En revanche, elle stockera uniquement ses données en cache (pas d'accès à la mémoire froide), et ne pourra globalement pas accéder à toutes les fonctionnalités du système d'exploitation.
## Conclusion et réflexion
Si on résume encore une fois l'évolution du développement web, on voit que :
1. L'infrastructure sur laquelle repose les sites web est toujours sensiblement la même : serveur d'un côté, client/navigateur de l'autre, le protocole HTTP qui transmet du code HTML entre les deux.
2. Les technologies pour mettre en place un site web, elles, ont pas mal changé : on est passé d'un client totalement passif qui se chargeait uniquement d'afficher les pages web à un client qui s'occupe tout seul de faire naviguer l'utilisateur⋅ice dans le site. De l'autre côté, le serveur qui était une machine à construire des pages HTML est devenu une machine à envoyer de la donnée à une SPA qu'il a servit en une seule fois au navigateur.
Très bien. Mais attention : il y a des excellentes raisons pour avoir fait ça... *pour certains types de sites*. Et c'est là qu'il faut selon moi prendre un peu de recul : on utilise aujourd'hui de SPA pour des besoins pas du tout justifiés, comme des blogs ou des pages perso, au point qu'on en oublie les désavantages non-négligeables de cette méthode de développement :
1. le temps passé et les compétences nécessaires pour le développement peuvent être assez élevés,
2. le volume d'une SPA peut être assez importante, jusqu'à plusieurs centaines de Mo, ce qui est énorme alors que beaucoup de besoins restent simples.
3. les technologies sont moins matures et évoluent beaucoup plus vite que pour le backend, ce qui veut dire que les applications frontend sont aussi rapidement obsolètes (apparition de bugs et de failles de sécurité) sans de gros efforts de maintenances.
Mais bon. Comme dit le proverbe :
> « Quand on a un marteau, tout ressemble à un clou. »
>
Et c'est particulièrement vrai pour les développeur⋅euses de manière générale.
Si on regarde les sites qu'on a l'habitude de visiter : des pages persos par exemple, ou des sites d'information, ou des wiki. Pour énormément de besoins, des technologies très pratiques existent déjà depuis longtemps, et permettent de rapidement faire beaucoup de choses. Je terminerai donc cette explication par un avis qui n'engage que moi : "la manière moderne de faire les choses", c'est souvent une manière de cacher un manque de réflexion sur deux questions : 1. de quoi j'ai besoin ? et 2. est-ce que les moyens que je me donne pour satisfaire ces besoins sont réellement adaptés ?
## Lexique
* serveur : machine accessible par le réseau, sur lequel tourne un programme qui sert des pages HTML.
* navigateur ou client : Programme qui permet d'afficher des pages HTML, stylisées avec du CSS, et d'exécuter du Javascript. Exemples de navigateurs : Firefox, Chrome, Chromium, Brave...
* module ou librairie : ensemble de classes et de fonctions réutilisables d'un programme à un autre.
* framework : ensemble de modules, combinée à une structure de projet définie, qui permet de rapidement réaliser des projets similaires.
* SPA : Single Page Application. Paquet de code Javascript qui contient toute la structure d'un site et qui remplace le code HTML lors de la navigation plutôt que d'exécuter des requêtes à chaque action.
* PWA : Progressive Web App. Une SPA accessible comme une application native une fois installée, par une icône sur un bureau par exemple.