GraphQL MySQL API with JWT Authentication and Rate Limiting
402
Here's a comprehensive Docker Hub description for your repository:
A robust, scalable, and secure GraphQL API built with PHP, MySQL, and Redis. This project leverages Docker for containerization, providing a seamless development and deployment experience. Key features include JWT-based authentication, comprehensive rate limiting, and support for dynamic queries across multiple database tables. The API dynamically exposes services based on the RDBMS database and table structures, making it highly adaptable and flexible.
The architecture consists of the following components:
Clone the repository:
git clone https://github.com/yourusername/graphql-mysql-api-jwt-rate-limit.git
cd graphql-mysql-api-jwt-rate-limit
Build and start the Docker containers:
docker-compose up -d --build
The configuration is managed through the config.php file. It includes settings for the MySQL database, JWT secret, and other relevant configurations.
config.php<?php
return [
'db' => [
'host' => 'db',
'user' => 'myuser',
'password' => 'mypassword',
'database' => 'mydatabase',
],
'jwt_secret' => 'your_jwt_secret',
];
Start the containers:
docker-compose up -d --build
Generate a JWT token:
Access the endpoint to generate a token:
curl http://localhost/GenerateToken.php
Copy the token from the response.
Make requests to the GraphQL endpoint:
curl -X POST -H "Content-Type: application/json" -H "Authorization: Bearer your-jwt-token" --data '{ "query": "{ products(page: 1) { products { productCode, productName }, total, page, token } }" }' http://localhost/api.php
The JWT tokens are used to authenticate API requests. The JwtHandler.php file handles the creation and validation of these tokens.
<?php
require 'JwtHandler.php';
$jwtHandler = new MyApp\JwtHandler('your_jwt_secret');
$token = $jwtHandler->encode(['sub' => 'user123']);
echo $token;
The token is validated in api.php by decoding it and checking its validity.
Rate limiting is implemented using Redis to ensure that each user cannot exceed a defined number of requests per second.
<?php
namespace MyApp;
class RateLimiter {
private $redis;
private $maxRequests;
private $windowSeconds;
public function __construct($host, $maxRequests, $windowSeconds) {
$this->redis = new \Redis();
$this->redis->connect($host);
$this->maxRequests = $maxRequests;
$this->windowSeconds = $windowSeconds;
}
public function isRateLimited($key, $service) {
$redisKey = "ratelimit:{$service}:{$key}";
$current = $this->redis->incr($redisKey);
if ($current == 1) {
$this->redis->expire($redisKey, $this->windowSeconds);
}
if ($current > $this->maxRequests) {
error_log("Rate limit exceeded for key: $redisKey");
return true;
}
error_log("Current count for key $redisKey: $current");
return false;
}
}
{
products(page: 1) {
products {
productCode
productName
}
total
page
token
}
}
curl -X POST -H "Content-Type: application/json" -H "Authorization: Bearer your-jwt-token" --data '{ "query": "{ products(page: 1) { products { productCode, productName }, total, page, token } }" }' http://localhost/api.php
curl --location 'http://localhost/api.php' \
--header 'Content-Type: application/json' \
--header 'Authorization: Bearer eyJ0eXAiOiJKV1QiLCJhbGciOiJIUzI1NiJ9.eyJpc3MiOiJodHRwOlwvXC9leGFtcGxlLm9yZyIsImF1ZCI6Imh0dHA6XC9cL2V4YW1wbGUuY29tIiwiaWF0IjoxNzE5NTk3MTU0LCJuYmYiOjE3MTk1OTcxNTQsInN1YiI6InVzZXIxMjMifQ.paf6YFnETH10TOGqZ5MKvOkZc1T6gIEwjL3tspXdgGI' \
--data '{"query":"{ customers(page: 1) { customers { customerNumber, customerName, phone }, total, page, token } }","variables":{}}'
Pagination is implemented to efficiently handle large sets of data. Each request includes the page parameter to specify the current page, and the response includes a new token for fetching subsequent pages.
Rate limiting is applied using Redis to restrict the number of API requests a user can make within a specified timeframe. The strategy involves incrementing a counter for each request and checking if it exceeds the maximum allowed requests.
Comprehensive error handling ensures that any issues encountered during request processing are properly logged and reported to the client with meaningful messages.
Content type
Image
Digest
sha256:9e2455ae0…
Size
173.7 MB
Last updated
about 2 years ago
docker pull apige/graphql-mysql-api-jwt-rate-limit