Plugin System
The gRPC-GraphQL Gateway includes a powerful plugin system that allows you to extend the gateway’s functionality by hooking into key lifecycle events.
Creating a Plugin
To create a plugin, implement the Plugin trait:
use grpc_graphql_gateway::plugin::Plugin;
use grpc_graphql_gateway::middleware::Context;
use async_graphql::{Request, Response};
use async_trait::async_trait;
pub struct MyPlugin;
#[async_trait]
impl Plugin for MyPlugin {
type Error = Box<dyn std::error::Error + Send + Sync>;
fn name(&self) -> &str {
"MyPlugin"
}
async fn on_request(&self, _ctx: &Context, req: &Request) -> Result<(), Self::Error> {
println!("Request received: {:?}", req.query);
Ok(())
}
async fn on_response(&self, _ctx: &Context, res: &Response) -> Result<(), Self::Error> {
println!("Response sent");
Ok(())
}
async fn on_subgraph_request(&self, service_name: &str, metadata: &mut tonic::metadata::MetadataMap) -> Result<(), Self::Error> {
println!("Sending request to subgraph: {}", service_name);
metadata.insert("x-custom-header", "value".parse().unwrap());
Ok(())
}
async fn on_schema_build(&self, builder: &mut grpc_graphql_gateway::schema::SchemaBuilder) -> Result<(), Self::Error> {
// Modify schema builder here
Ok(())
}
}
Hook Points
The following hooks are available:
on_request: Called before the GraphQL request is executed.on_response: Called after the GraphQL request is executed.on_schema_build: Called during schema construction (allows modifying the schema).on_subgraph_request: Called before a gRPC request is sent to a subgraph service.
Registering Plugins
Register plugins using GatewayBuilder:
let gateway = Gateway::builder()
.register_plugin(MyPlugin)
.build()?;
Dynamic Loading via Feature Flags
You can use Cargo features to conditionally compile and enable plugins.
In Cargo.toml:
[features]
my-plugin = []
In your code:
#[cfg(feature = "my-plugin")]
builder = builder.register_plugin(MyPlugin);