2017-08-08 1 views
0

Je travaille sur un nouveau projet basé sur les microservices. C'est une application interne et seulement environ 10 microservices. Nous utiliserons une API de passerelle pour l'authentification et éventuellement l'agrégation de microservices. (Probablement Netflix zuul avec Spring Boot)Test A/B. Routage de clients dans une API de passerelle

Ce que je ne comprends pas, c'est comment nous faisons le routage pour les tests A/B et Canary. Supposons que j'ai 100 clients et que nous voulons tester A/B une nouvelle version d'un microservice. L'application client n'a pas besoin de modifications, il s'agit uniquement de modifications internes apportées à la fonction fournie par le microservice. Je comprends que nous défendrions un nouveau microservice qui est (par exemple) v2. Ce que je suis intrigué, c'est comment puis-je diriger (disons) les clients 1-10 vers la nouvelle version. Nous devons pouvoir configurer cela de manière centralisée et ne rien changer au client.

Nous connaissons leurs adresses mac (ainsi que d'autres attributs d'identification) et pouvons insérer n'importe quel type d'en-tête que nous voulons identifier leurs messages.

Alors, comment les rediriger vers la version 2 de l'API pour le test A/B ou le déploiement Canaries?

Répondre

0

Si décrire le haut niveau, approche générique, vous pouvez faire quelque chose comme ceci:

  1. vos clients ont besoin d'avoir des paramètres qui permettront de les identifier de manière unique. On dirait que tu l'as déjà.
  2. Implémentez un service API supplémentaire (appelons-le Experiment API). Ce service doit avoir au moins un point d'extrémité qui reçoit les attributs d'identification du client et indique si le client est impliqué dans le test A/B ou non.
  3. Lors de chaque requête entrante, l'API Gateway doit utiliser ce point de terminaison API Experiment pour déterminer quelle version de microservice (v1 ou v2) utilise pour rediriger/appeler.
  4. Pour éviter d'appeler l'API Experiment chaque fois que vous introduisez une couche de mise en cache dans l'API Gateway. Comme autre option, vous pouvez utiliser un cookie personnalisé (qui contient si client sous "expérience"), n'appelez à l'API Experiment que si ce cookie n'est pas spécifié et renvoyez le cookie au client avec la réponse.
0

Pour exposer un peu la réponse de @ Set. Vous devrez introduire du code d'instrumentation dans votre API de passerelle pour prendre la décision sur le point de terminaison en aval à appeler. Si, et seulement si, le seul composant de votre backend distribué concerné est l'API de la passerelle, la solution ci-dessus est sur-conçue: vous pouvez vous contenter d'une bibliothèque. Mais il est probable que vous découvrirez bientôt qu'un ou plusieurs de vos autres services ont besoin de connaître l'expérience, auquel cas vous avez besoin d'un service autonome.

De manière générale, la construction d'un cadre d'expérimentation robuste est une tâche difficile. Vous rencontrerez rapidement des problèmes inattendus, par ex. expérience de la stabilité (comment garantir la même expérience pour le retour des visiteurs) ou comment changer la proportion d'allocation (ou peut-être désactiver complètement le nouveau code) sans avoir besoin de redémarrer l'application hôte. Vous devriez étudier les frameworks open source, ou même l'instrumentation côté serveur commercial. (Nous en avons un au Variant).

0

J'ai publié un prototype sur Github qui montre comment vous pouvez réaliser le routage en utilisant un Zuul Gateway. Ce prototype montre simplement comment vous pouvez router le trafic basé sur un cookie vers différentes instances de la même application. Vous pouvez effectuer le routage en fonction d'autres critères. Vous devriez également jeter un oeil à Spring Cloud Gateway comme alternative à Zuul. Semble être très prometteur.Une configuration plus simple consisterait simplement à ajouter nginx devant votre service et à utiliser la méthode split_clients.

http { 
    # ... 
    # application version 1a 
    upstream version_1a { 
     server 10.0.0.100:3001; 
     server 10.0.0.101:3001; 
    } 

    # application version 1b 
    upstream version_1b { 
     server 10.0.0.104:6002; 
     server 10.0.0.105:6002; 
    } 

    split_clients "${arg_token}" $appversion { 
     95%  version_1a; 
     *  version_1b; 
    } 

    server { 
     # ... 
     listen 80; 
     location/{ 
      proxy_set_header Host $host; 
      proxy_pass http://$appversion; 
     } 
    } 
} 

https://www.nginx.com/blog/performing-a-b-testing-nginx-plus/