Blogue
Protection efficace contre les attaques DDoS des services API avec Cloudflare

Protection efficace contre les attaques DDoS des services API avec Cloudflare

Daniel Yavorovych
November 9, 2020

Problème

Aujourd'hui, les applications sont souvent divisées en applications frontales et API dorsales.

Le front-end est généralement stocké dans Object Storage (tel qu'AWS S3 ou Google Cloud Storage), et un CDN est configuré devant lui (tel que CloudFront ou le même CloudFlare). Ce système a fait ses preuves et, avec le DDoS, une telle ressource est inefficace. Même si les attaques DDoS sont vraiment puissantes, CloudFlare fait un excellent travail en filtrant le trafic indésirable, incitant les utilisateurs à reCAPTCHA en dernier recours.

Mais en ce qui concerne les services d'API, la situation est pire. Même après avoir réussi un défi js dans un navigateur, un utilisateur valide ne peut pas toujours accéder facilement au service d'API derrière CloudFlare dans Attaqué mode.

Si nous parlons d'API utilisées par d'autres services qui n'ont pas de travail interactif (robots divers, services personnalisés, etc.), activez le Attaqué le mode d'une API peut équivaloir à bloquer l'accès à celle-ci.

Que faire dans ce cas ?

CloudFlare possède lui-même un article sur la ressource de support. Il recommande simplement d'abaisser le Niveau de sécurité aux points de terminaison de l'API, en désactivant Toujours en ligne mode, désactivation Mise en cache, et désactivant Vérification de l'intégrité du navigateur.

Bien entendu, cela aidera à résoudre le problème du blocage indésirable des API, mais cela réduira tellement le niveau de protection que votre backend d'API risque d'être surchargé et même de vous refuser le service.

Dans cet article, nous examinerons deux méthodes qui vous permettront de filtrer 100% du trafic indésirable et d'éliminer complètement les faux positifs et le blocage des demandes valides des utilisateurs.

Idée

Comme le titre l'indique, nous transférons la validation principale des demandes du côté CloudFlare, en ne transmettant que les clés d'API enregistrées dans votre application.

Cette méthode ne convient qu'aux API privées (qui sont les plus populaires). Si vous utilisez une API publique où n'importe qui peut adresser une demande à votre service, vous devez être prêt à faire face à un afflux de trafic indésirable. Cette pratique de ces dernières années montre que même les API publiques passent au modèle d'accès par jeton, qui ne peut être obtenu qu'après enregistrement. Cela vous permet de mieux contrôler le processus des services fournis et, en même temps, de configurer la protection contre les attaques.

Mise en œuvre

CloudFlare propose un support sans serveur : Travailleurs de Cloudflare. Il s'agit d'un outil vraiment puissant et flexible qui a également un prix très bas (de 0 à 5$ par mois, aucun dépassement de trafic). Plus récemment, Cloudflare propose un service supplémentaire : stockage des valeurs clés, qui vous permet d'y accéder directement depuis les collaborateurs de CloudFlare.

Ces deux technologies nous aideront à implémenter notre filtre principal :

Effective API service DDOS protection with CloudFlare

Comme le montre le schéma ci-dessus, nous utilisons Cloudflare Workers pour vérifier la présence d'une clé API dans la base de données Key-Value. Si la clé n'est pas présente dans la demande, ou si elle ne se trouve pas dans le KV-Store, le client recevra un statut HTTP 403. Si la clé est spécifiée correctement, la demande sera transmise par proxy au backend, comme d'habitude.

Une attention particulière doit être portée à Script de synchronisation des clés de l'API. Il s'agit d'un script qui doit conserver la liste des clés dans Cloudflare IV à jour, ce qui signifie que dès qu'une clé est ajoutée dans votre application ou bloquée/supprimée, son état doit être reflété dans Cloudflare IV dès que possible.

Idéalement, ce processus se déroule en temps réel.

Instructions étape par étape

  • Connectez-vous au Tableau de bord Cloudflare
  • Sélectionnez le domaine
  • Accédez à Travailleurs
  • Cliquez Gérez les travailleurs
  • Accéder à l'onglet KV et créez un nouvel espace de noms (avec nom jetons, par exemple)
  • Retourner au Travailleur onglet et cliquez Créer un travailleur
  • Entrez le code suivant et cliquez sur Sauvegardez et déployez

Code :


async function handleRequest(request) {
    const {searchParams} = new URL(request.url)
    const key = searchParams.get(API_KEY_NAME)
    const isKeyPresent = await TOKENS_KV.get(key)

if (!key || !isKeyPresent) {
        const data = {
            "status": "REQUEST_DENIED",
            "error_message": "Access denied."
        }
        const json = JSON.stringify(data, null, 2)
        
        return new Response(json, {
            status: 403,
            headers: {
                "content-type": "application/json;charset=UTF-8"
            }
        })
    }
    return await fetch(request)
}

addEventListener("fetch", event => {
        event.respondWith(handleRequest(event.request))
})
  • Accédez au Réglages onglet de la page du nouveau travailleur
  • Dans la section Variables d'environnement, ajoutez la variable d'environnement API_KEY_NAME, avec le nom de votre clé d'API comme valeur
  • Dans la section Liaison d'espace de noms KV, créez la variable d'environnement TOKENS_KV, et dans Value, sélectionnez Créer espace de noms KV. Enfin, veuillez cliquer Enregistrer pour enregistrer les modifications.
  • Il est maintenant temps de synchroniser les clés d'API de votre application avec Cloudflare IV. Cela peut être fait à l'aide du API Cloudflare. Je vais fournir un exemple de code Python utilisé par le client officiel de Cloudflare.
  • CF_ACCOUNT_ID que vous pouvez obtenir en utilisant documentation
  • CF_API_TOKEN également décrit dans doc
  • CF_KV_NAMESPACE_ID - il s'agit de l'ID de l'espace de noms KV jetons, disponible sur la page des paramètres KV

Code :


import logging
import CloudFlare‍

class CF:
    CF_ACCOUNT_ID = ''
    CF_API_TOKEN = ''
    CF_KV_NAMESPACE_ID = ''‍
    
    def __init__(self):
        self.cf = CloudFlare.CloudFlare(token=self.CF_API_TOKEN)‍
    
    def get_active_tokens_list():
        """
        Need define
        """
        return []
    
    def get_tokens(self):
        return [i['name'] for i in
                self.cf.accounts.storage.kv.namespaces.keys.get(self.CF_ACCOUNT_ID, self.CF_KV_NAMESPACE_ID)]
    def create_tokens(self, tokens):
        data = [{"key": token, "value": "enabled"} for token in tokens]
        self.cf.accounts.storage.kv.namespaces.bulk.put(self.CF_ACCOUNT_ID, self.CF_KV_NAMESPACE_ID, data=data)‍
    
    def delete_tokens(self, tokens):
        self.cf.accounts.storage.kv.namespaces.bulk.delete(self.CF_ACCOUNT_ID, self.CF_KV_NAMESPACE_ID,
                                                            data=list(tokens))‍
    def update_tokens(self):
        old_tokens = set(self.get_tokens())
        new_tokens = set(self.get_active_tokens_list())
        to_delete_tokens = old_tokens - new_tokens‍
        
        self.delete_tokens(to_delete_tokens)
        self.create_tokens(new_tokens)‍
        
        logging.info('CF KV tokens update status: {old} old / {new} new / {deleted} deleted'.format(old=len(old_tokens),
                                                                                                    new=len(new_tokens),
                                                                                                    deleted=len(to_delete_tokens)))

if __name__ == '__main__':
    c = CF()
    c.update_tokens()
  • La dernière étape consiste à revenir au menu principal du domaine Cloudflare dans la section Workers et à cliquer sur Ajouter un itinéraire bouton. Spécifiez le point de terminaison de l'API à filtrer par notre nouveau collaborateur et sélectionnez le collaborateur créé dans la liste en cliquant sur Enregistrer pour enregistrer les règles de routage.
  • Si vous avez un trafic élevé, il est probablement judicieux de passer immédiatement au plan payant Cloudflare Workers afin de ne pas avoir de problèmes avec la limite épuisée. En savoir plus sur la tarification : https://developers.cloudflare.com/workers/platform/pricing
  • Bien entendu, après la mise en œuvre de cette décision, le niveau de protection devrait être abaissé et toutes les autres recommandations spécifiées dans https://support.cloudflare.com/hc/en-us/articles/200504045-Using-Cloudflare-with-your-API pour les points de terminaison de l'API. Le bonus sera que désormais la ressource transmettra non seulement le trafic valide, mais filtrera également le trafic non valide.

Questions et réponses

Q : Mais comment puis-je donner à Cloudflare l'accès à toutes les clés d'API de mon service ? Ce n'est pas sûr !

R : Vous autorisez déjà Cloudflare à accéder à l'ensemble de votre trafic en le configurant en mode proxy. Et pas seulement toi. Selon les recherches, Cloudflare est utilisé par 80,9 % de tous les sites web dont nous connaissons le service de proxy inverse. Cela représente 14,7 % de tous les sites Web.

Conclusion

La méthode décrite a été appliquée par nous dans la pratique pour un service d'API qui a succombé à une attaque DDoS de plusieurs milliards de requêtes par jour (avec une charge normale de dizaines de milliers de requêtes par jour).

Cette solution a repoussé l'attaque à 100 % et n'a pas bloqué les demandes réelles des utilisateurs. Dans le même temps, les coûts étaient ridicules, allant jusqu'à 50 dollars par mois (pour une utilisation excessive des demandes adressées aux employés de Cloudflare, qui est incluse dans les frais de 5 dollars par mois au moment de l'attaque). De là, nous pouvons juger qu'une telle solution est non seulement très efficace, mais également l'option la plus budgétaire pour protéger l'API). À titre de comparaison, des services spécialisés visant à protéger les API contre les attaques DDoS sur ce trafic coûteraient entre 800 et 1 500 dollars pour les mêmes volumes. Dans le même temps, nous sommes conscients du potentiel de CloudFlare et nous pouvons être sûrs que cette solution vous protégera contre des attaques de plus en plus massives.

Daniel Yavorovych
CTO and Co-founder at Dysnix
Brainpower and problem-solver, meditating and mountain hiking.
Table des matières
Articles connexes
Abonnez-vous au blog
La meilleure source d'informations pour le service client, les conseils de vente, les guides et les meilleures pratiques du secteur. Joignez-vous à nous.
Merci de votre inscription au blog Dysnix
Vous serez désormais le premier à savoir quand nous publierons un nouvel article
J'ai compris
Oups ! Une erreur s'est produite lors de l'envoi du formulaire.
Copié dans le presse-papiers
Collez-le où vous voulez