Line data Source code
1 : use crate::build_info::{BuildInfo as BuildInfoObject, BuildInfoProvider};
2 : use async_graphql::http::{playground_source, GraphQLPlaygroundConfig};
3 : use async_graphql::{Context, EmptySubscription, Object, Result, Schema};
4 : use async_graphql_axum::{GraphQLRequest, GraphQLResponse};
5 : use axum::extract::Extension;
6 : use axum::response::{Html, IntoResponse};
7 :
8 : /// The schema type with Query and Mutation roots
9 : pub type ApiSchema = Schema<QueryRoot, MutationRoot, EmptySubscription>;
10 :
11 : /// Query root for the GraphQL API
12 : pub struct QueryRoot;
13 :
14 : #[Object]
15 : impl QueryRoot {
16 : /// Returns build metadata for the running service
17 : #[allow(clippy::unused_async)]
18 6 : async fn build_info(&self, ctx: &Context<'_>) -> Result<BuildInfoObject> {
19 6 : let provider = ctx.data::<BuildInfoProvider>()?;
20 6 : Ok(provider.build_info())
21 6 : }
22 : }
23 :
24 : /// Mutation root for the GraphQL API
25 : pub struct MutationRoot;
26 :
27 : #[Object]
28 : impl MutationRoot {
29 : /// Placeholder mutation - returns the input string
30 : ///
31 : /// This exists because GraphQL requires at least one mutation.
32 : /// Replace with actual mutations as features are implemented.
33 : #[allow(clippy::unused_async)]
34 : async fn echo(&self, _ctx: &Context<'_>, message: String) -> String {
35 : message
36 : }
37 : }
38 :
39 : /// GraphQL playground handler - serves the interactive GraphQL IDE
40 : #[allow(clippy::unused_async)]
41 15 : pub async fn graphql_playground() -> impl IntoResponse {
42 15 : Html(playground_source(GraphQLPlaygroundConfig::new("/graphql")))
43 15 : }
44 :
45 : /// GraphQL request handler - executes GraphQL queries and mutations
46 11 : pub async fn graphql_handler(schema: Extension<ApiSchema>, req: GraphQLRequest) -> GraphQLResponse {
47 11 : schema.execute(req.into_inner()).await.into()
48 11 : }
|