JavaScript : un langage synchrone ou asynchrone ?

Anastasia Frezefond
3 min readJun 20, 2023

--

“P’têt ben qu’oui, p’têt ben qu’non”, j’ai envie de vous dire ! JavaScript est en fait un langage à la fois synchrone et asynchrone.

JavaScript un langage principalement synchrone

Avec JavaScript, les instructions sont exécutées de manière séquentielle, une après l’autre, dans l’ordre dans lequel elles sont écrites. Cela signifie que chaque instruction doit être complètement terminée avant que l’instruction suivante puisse être exécutée. Voici un exemple de code synchrone :

function greet(name) {
return "Bonjour, " + name + "!";
}

var message = greet("John");
console.log(message);

Dans ce cas de figure, l’exécution des instructions bloque l’exécution des instructions suivantes jusqu’à ce qu’elles soient terminées.

Du coup vous vous doutez que si une instruction prend du temps à s’exécuter, elle bloque l’exécution du reste du programme, ce qui peut entraîner des temps d’attente et une utilisation inefficace des ressources et donc des performances réduites. Pas génial ! ☹️

Plot twist : JavaScript également capable d’exécuter des opérations asynchrones

Pour gérer les opérations asynchrones et les tâches longues de manière plus efficace, de nombreux langages de programmation, y compris JavaScript, offrent des mécanismes pour permettre une exécution asynchrone / non bloquante du code.

L’asynchronisme en JavaScript est géré principalement grâce à des fonctions de rappel (callbacks), des promesses (promises) et des fonctions asynchrones (async/await) introduites dans les versions récentes d’ECMAScript (ES6+).

Cela est particulièrement utile lors de l’exécution de tâches longues ou potentiellement bloquantes, telles que les requêtes réseau, les accès aux fichiers …

Du coup c’est quoi les callbacks

Cela permet de spécifier une fonction à exécuter une fois qu’une opération asynchrone est terminée. Voici un exemple concret :

function greet(name, callback) {
var message = "Bonjour, " + name + "!";
callback(message);
}

function displayMessage(message) {
console.log(message);
}

greet("John", displayMessage);

C’est un exemple simple de callback où une fonction est passée en tant qu’argument à une autre fonction et est appelée à un moment spécifié, dans ce cas précisément pour afficher le message.

Les promesses / promises

A prononcer PRO-MA-I-ZE ! 🫣 Par rapport aux callbacks on va avoir une syntaxe plus élégante pour gérer les opérations asynchrones en utilisant des objets qui représentent une valeur qui peut être disponible maintenant, dans le futur ou jamais.

Une instance de la classe Promise en JavaScript possède plusieurs méthodes qui permettent de gérer les résultats et les erreurs associés à l'opération asynchrone.

var myPromise = new Promise(function(resolve, reject) {
// Logique asynchrone
});

myPromise.then(function(result) {
// Gestion de la réussite
}).catch(function(error) {
// Gestion de l'échec
}).finally(function() {
// Gestion finale
});
  1. then(onFulfilled, onRejected): Attache un gestionnaire de réussite (onFulfilled) et un gestionnaire d'échec (onRejected) à la Promise. Ces gestionnaires sont appelés lorsque la Promise est résolue avec succès (via resolve) ou lorsqu'une erreur se produit (via reject).
  2. catch(onRejected): Attache un gestionnaire d'échec (onRejected) à la Promise. Ce gestionnaire est appelé uniquement en cas d'erreur lors de l'exécution de la Promise.
  3. finally(onFinally): Attache un gestionnaire (onFinally) qui est appelé lorsque la Promise est résolue ou rejetée, quel que soit le résultat. Il est souvent utilisé pour effectuer des actions de nettoyage ou de finalisation.

Voici un exemple concret :

function greet(name) {
return new Promise(function(resolve, reject) {
var message = "Bonjour, " + name + "!";
resolve(message);
});
}

function displayMessage(message) {
console.log(message);
}

greet("John")
.then(displayMessage)
.catch(function(error) {
console.error("Une erreur s'est produite : " + error);
});

Enfin, les fonctions asynchrones !

Les fonctions asynchrones, quant à elles, permettent d’écrire du code asynchrone de manière plus synchrone en utilisant les mots-clés async et await. Voici un exemple de fonction asynchrone pour une requête HTTP :


async function effectuerRequete() {
try {
const reponse = await fetch('https://api.exemplemedium.com/test');
// Await spécifie que le programme doit attendre la réponse de la requête
const donnees = await reponse.json();
// Ici qu'il doit attendre la conversion de la réponse en JSON
console.log(donnees);
} catch (erreur) {
console.error('Erreur lors de la requête :', erreur);
}
}

effectuerRequete();

L’utilisation de await permet donc de suspendre l'exécution de la fonction asynchrone jusqu'à ce que la promesse soit résolue (c'est-à-dire que la requête se termine avec succès) ou rejetée (en cas d'erreur).

En utilisant try/catch, il est ainsi possible de capturer et gérer les éventuelles erreurs qui se produisent pendant l'exécution de la fonction asynchrone.

Pour finir

Même si JavaScript peut exécuter des tâches asynchrones, il reste globalement un langage qui n’exécute qu’une seule instruction à la fois dans le fil d’exécution principal (thread principal). Les tâches asynchrones sont gérées par le moteur JavaScript, qui utilise des mécanismes sous-jacents tels que les événements, les timers…

--

--