L'en-tête Access-Control-Allow-Origin expliqué - avec un exemple CORS

Souvent, lors de l'appel d'une API, vous pouvez voir une erreur dans votre console qui ressemble à ceci:

 Access to fetch at '//somesite.com' from origin '//yoursite.com' has been blocked by CORS policy: The 'Access-Control-Allow-Origin' header has a value that is not equal to the supplied origin 

Dans cet article, nous allons apprendre pourquoi cette erreur se produit et comment vous pouvez la corriger.

Quel est l'en- Access-Control-Allow-Origintête?

Access-Control-Allow-Originest un en-tête CORS. CORS, ou Cross Origin Resource Sharing, est un mécanisme permettant aux navigateurs de permettre à un site s'exécutant à l'origine A de demander des ressources à l'origine B.

L'origine n'est pas seulement le nom d'hôte, mais une combinaison de port, de nom d'hôte et de schéma, tel que - //mysite.example.com:8080/

Voici un exemple où cela entre en action -

  1. J'ai une origine A: //mysite.comet je veux obtenir des ressources d'origine B: //yoursite.com.
  2. Pour protéger votre sécurité, le navigateur ne me laissera pas accéder aux ressources de yoursite.com et bloquera ma demande.
  3. Afin de permettre à l'origine A d'accéder à vos ressources, votre origine B devra informer le navigateur que je peux obtenir des ressources de votre origine.

Voici un exemple de Mozilla Developer Network qui explique très bien cela:

Avec l'aide de CORS, les navigateurs permettent aux origines de partager des ressources entre elles.

Il existe quelques en-têtes qui permettent le partage des ressources entre les origines, mais le principal est Access-Control-Allow-Origin. Cela indique au navigateur quelles origines sont autorisées à recevoir des requêtes de ce serveur.

Qui a besoin de définir Access-Control-Allow-Origin?

Pour comprendre qui doit définir cet en-tête, considérez ce scénario: Vous naviguez sur un site Web utilisé pour afficher et écouter des chansons. Le site Web tente de se connecter à votre banque en arrière-plan de manière malveillante.

Alors, qui a la capacité ultime d'empêcher ce site Web malveillant de voler vos données à la banque? La Banque! Ainsi, la banque devra protéger ses ressources en définissant l'en- Access-Control-Allow-Origintête dans le cadre de la réponse.

N'oubliez pas: l'origine responsable du service des ressources devra définir cet en-tête.

Comment utiliser et quand passer cet en-tête

Voici un exemple de valeurs que vous pouvez définir:

  1. Access-Control-Allow-Origin : * : Autorise n'importe quelle origine.
  2. Access-Control-Allow-Origin : //mysite.com : Autoriser les demandes uniquement de mysite.com.

Voyez-le en action

Regardons un exemple. Vous pouvez consulter ce code sur mon dépôt GitHub.

Nous allons construire un serveur sur l'origine A //localhost:8000qui enverra une chaîne de Hellos à un apipoint final. Nous allons appeler avec ce point de terminaison en créant un client sur l'origine B //localhost:3000, puis en utilisant fetch pour demander la ressource. On s'attend à voir la chaîne Hellopassée par l'origine A dans la console du navigateur d'origine B.

Disons que nous avons une origine //localhost:8000qui sert cette ressource sur le /apipoint de terminaison. Le serveur envoie une réponse avec l'en-tête Access-Control-Allow-Origin.

const express = require("express"); const app = express(); const port = process.env.SERVER_PORT || 8000; // Add Access Control Allow Origin headers app.use((req, res, next) => { res.setHeader("Access-Control-Allow-Origin", "//yoursite.com"); res.header( "Access-Control-Allow-Headers", "Origin, X-Requested-With, Content-Type, Accept" ); next(); }); app.get("/api", (req, res) => { res.json("Hello"); }); app.listen(port, () => console.log(`Listening on port ${port}`)); 

Du côté client, vous pouvez appeler ce point de terminaison en appelant fetchcomme ceci:

fetch('//localhost:8000/api') .then(res => res.json()) .then(res => console.log(res)); 

Ouvrez maintenant la console de votre navigateur pour voir le résultat.

Étant donné que l'en-tête est actuellement défini pour autoriser l'accès uniquement à partir de //yoursite.com, le navigateur bloquera l'accès à la ressource et vous verrez une erreur dans votre console.

Maintenant, pour résoudre ce problème, modifiez les en-têtes comme suit:

 res.setHeader("Access-Control-Allow-Origin", "*"); 

Vérifiez la console de votre navigateur et vous pourrez maintenant voir la chaîne Hello.

Intéressé par plus de tutoriels et JSBytes de ma part? Inscrivez-vous à ma newsletter.