Mit der Popularität von Cloud Computing und Microservice-Architektur ist das API-Gateway ein unverzichtbarer Bestandteil des Microservice-Systems und seine Funktionen werden immer wichtiger. Das API-Gateway kann alle Anfragen innerhalb und aus dem System abfangen und weiterleiten und ist für Sicherheit, Zugriffskontrolle, Verkehrskontrolle, Lastausgleich und andere Funktionen verantwortlich.
In diesem Artikel stellen wir vor, wie Sie mit PHP7.0 ein einfaches API-Gateway implementieren, um die folgenden Funktionen zu erreichen:
Bevor Sie beginnen, stellen Sie bitte sicher, dass die folgende Software installiert ist:
Schritt 1: Schreiben Sie ein einfaches API-Gateway
Zunächst müssen wir ein einfaches API-Gateway für die Weiterleitung von Anforderungen an den Microservice erstellen. Für das Routing verwenden wir die Symfony Routing Component.
Erstellen Sie eine neue PHP-Datei, zum Beispiel index.php, und fügen Sie den folgenden Code hinzu:
require_once 'vendor/autoload.php'; use SymfonyComponentRoutingRouteCollection; use SymfonyComponentRoutingRoute; use SymfonyComponentHttpFoundationRequest; use SymfonyComponentHttpFoundationResponse; use SymfonyComponentRoutingMatcherUrlMatcher; use SymfonyComponentRoutingExceptionResourceNotFoundException; $routes = new RouteCollection(); $routes->add('hello', new Route('/hello/{name}', array( 'controller' => function ($request) { return new Response(sprintf("Hello, %s!", $request->attributes->get('name'))); } ))); $matcher = new UrlMatcher($routes, getRequest()); try { $request = Request::createFromGlobals(); $parameters = $matcher->matchRequest($request); $response = call_user_func($parameters['controller'], $request); } catch (ResourceNotFoundException $exception) { $response = new Response('Not Found', Response::HTTP_NOT_FOUND); } catch (Exception $exception) { $response = new Response('An error occurred', Response::HTTP_INTERNAL_SERVER_ERROR); } $response->send();
In diesem Code haben wir eine Route namens „hello“ erstellt, die die Anfrage an eine anonyme Controller-Methodenmitte weiterleitet. Wenn diese Route verarbeitet wird, wird in der Antwort „Hallo, {name}!“ zurückgegeben, wobei {name} der Routenparameter ist.
Wir verwenden die Request- und Response-Klassen von Symfony, um HTTP-Anfragen und -Antworten zu erstellen und zu senden. Die Routing-Komponente von Symfony ist dafür verantwortlich, Anfragen an passende Routen weiterzuleiten und passende Controller-Methoden aufzurufen.
An diesem Punkt können wir diese Datei ausführen und http://localhost:8080/hello/world besuchen und die Ausgabe „Hello, world!“ sehen.
Schritt 2: Strombegrenzungsfunktion hinzufügen
Wir hoffen, dass das API-Gateway die Anforderungen jeder API begrenzen kann, um das Risiko einer Überlastung auf der Serverseite zu verringern. Zu diesem Zweck können wir Redis verwenden, um Drosselungszähler für jede API zu speichern.
Zuerst müssen wir Predis mit Composer installieren, einer Redis-Clientbibliothek in PHP:
composer require predis/predis
Fügen Sie dann den folgenden Code in index.php hinzu, um den Zähler vor jeder Microservice-Anfrage zu überprüfen:
use PredisClient; // ... $redis = new Client(); // Limit requests to 100 per minute per user. $maxRequests = 100; $timeWindow = 60; // seconds $ip = $_SERVER['REMOTE_ADDR']; $key = "ratelimit:{$ip}"; $currentRequests = $redis->incr($key); $redis->expire($key, $timeWindow); if ($currentRequests > $maxRequests) { $response = new Response('Rate limit exceeded', Response::HTTP_TOO_MANY_REQUESTS); $response->headers->set('Retry-After', $timeWindow); $response->send(); exit; }
In diesem Code Wir verwenden den Predis-Client, um eine Verbindung zum Redis-Server herzustellen und verwenden die IP-Adresse jeder Anfrage als Schlüsselnamen. Wir legen ein Limit von 100 Anfragen pro Minute und Benutzer fest und verwenden die Incr-Funktion, um den Zähler zu erhöhen.
Wenn der aktuelle Wert des Zählers den Höchstwert überschreitet, wird eine HTTP 429 „Too Many Requests“-Antwort zurückgegeben und der „Retry-After“-Header wird gesetzt, um den Client zu benachrichtigen, wann er die Anfrage erneut versuchen soll.
Schritt 3: Authentifizierungs- und Autorisierungsfunktionen hinzufügen
Außerdem müssen wir für jede API-Anfrage grundlegende Authentifizierungs- und Autorisierungsfunktionen hinzufügen. Hierzu verwenden wir den JSON Web Token (JWT)-Standard.
Um JWT zu verwenden, installieren Sie bitte zuerst die Firebase/php-jwt-Bibliothek:
composer require firebase/php-jwt
Fügen Sie dann den folgenden Code in index.php hinzu, um die JWT-Standardauthentifizierung und -Autorisierung zu implementieren:
use FirebaseJWTJWT; // ... $key = 'secret'; $token = $_SERVER['HTTP_AUTHORIZATION'] ?? ''; if ($token) { try { $decoded = JWT::decode($token, $key, array('HS256')); $user_id = $decoded->sub; $roles = $decoded->roles; } catch (Exception $e) { $response = new Response('Invalid token', Response::HTTP_UNAUTHORIZED); $response->send(); exit; } // Check user roles and permissions here... } else { $response = new Response('Token required', Response::HTTP_UNAUTHORIZED); $response->send(); exit; }
In diesem Code verwenden wir ein extrahiertes JWT-Token aus HTTP-Headern, um die Anfrage zu identifizieren und zu authentifizieren. Wir verwenden die JWT-Bibliothek, um das Token zu dekodieren und die Signatur und Gültigkeit zu überprüfen. Wenn das Token gültig ist, werden die Benutzer-ID und Rolleninformationen daraus extrahiert und seine Berechtigungen überprüft. Wenn das Token ungültig ist, wird eine HTTP 401 „Unauthorized“-Antwort zurückgegeben.
Schritt 4: Statistikfunktion hinzufügen
Abschließend fügen wir eine einfache Statistikfunktion hinzu, um die API-Nutzung aufzuzeichnen. Dazu werden wir Redis verwenden, um Metriken wie die Anzahl der Anfragen und Antwortzeiten zu speichern.
Zuerst müssen wir die phpredis-Erweiterung installieren:
sudo apt-get install php7.0-redis
Dann fügen Sie den folgenden Code in index.php hinzu, um die Statistiken jeder Anfrage aufzuzeichnen:
use PredisClient; // ... $redis = new Client(); $ip = $_SERVER['REMOTE_ADDR']; $key = "stats:{$ip}"; $now = time(); $timestamp = strtotime(date('Y-m-d H:i:00', $now)); $redis->zincrby($key, 1, $timestamp); $redis->expire($key, 3600);
In diesem Code berücksichtigen wir jede IP-Adresse (d. h. jeden Benutzer) , und verwenden Sie den ZINCRBY-Befehl von Redis, um den Wert des Anforderungszählers um 1 zu erhöhen. Wir verwenden auch die Festlegung der Ablaufzeit in Redis, um abgelaufene Datensätze zu löschen.
Schritt 5: API Gateway bereitstellen
Jetzt haben wir unserem API Gateway grundlegende Funktionen wie Routing, Einschränkungen, Authentifizierung, Autorisierung und Statistiken hinzugefügt. Wir können es mit einem herkömmlichen Webserver wie Apache oder Nginx bereitstellen oder den integrierten PHP-Server zum Testen verwenden.
Führen Sie zunächst den folgenden Befehl im Terminal aus, um den in PHP integrierten Server zu starten und ihn auf unsere index.php-Datei zu verweisen:
php -S localhost:8080
Dann können wir http://localhost:8080/ im Browser aufrufen und Fügen Sie Routen wie /hello/world zum URL-Pfad hinzu, um verschiedene Funktionen des API-Gateways zu testen.
Zusammenfassung
In diesem Artikel verwenden wir PHP7.0 und verschiedene Open-Source-Bibliotheken, um ein grundlegendes API-Gateway zu implementieren und grundlegende Funktionen wie Einschränkungen, Authentifizierung, Autorisierung und Statistiken hinzuzufügen. Das API-Gateway ist ein integraler Bestandteil der Microservices-Architektur, der uns dabei helfen kann, bessere Leistung, Sicherheit und Skalierbarkeit zu erreichen.
Tatsächlich stehen mittlerweile viele leistungsstarke API-Gateway-Lösungen zur Auswahl, wie Kong, Tyk, AWS API Gateway usw., die erweiterte Funktionen und Integrationen wie Lastausgleich, Caching, Sicherheit, Überwachung und Verwaltungswartezeit bieten.
Es ist jedoch immer noch wertvoll zu wissen, wie man ein API-Gateway mithilfe von Bibliotheken wie PHP und Symfony erstellt, und es ist eine ausgezeichnete Option, wenn Sie schnell ein einfaches API-Gateway erstellen müssen.
Das obige ist der detaillierte Inhalt vonWie implementiert man mit PHP7.0 ein API-Gateway mit Microservice-Architektur?. Für weitere Informationen folgen Sie bitte anderen verwandten Artikeln auf der PHP chinesischen Website!