You are viewing a plain text version of this content. The canonical link for it is here.
Posted to commits@camel.apache.org by je...@apache.org on 2021/08/16 20:21:12 UTC

[camel] branch main updated (001dc5e -> ff30215)

This is an automated email from the ASF dual-hosted git repository.

jeremyross pushed a change to branch main
in repository https://gitbox.apache.org/repos/asf/camel.git.


    from 001dc5e  CAMEL-16847: upgrade fabric8's  Kubernetes client to the latest version (#5956)
     new dff5afb  CAMEL-15864: camel-graphql - Supply variables in header or body.
     new ff30215  CAMEL-16122: camel-graphql - Supply query via body or header.

The 2 revisions listed above as "new" are entirely new to this
repository and will be described in separate emails.  The revisions
listed as "add" were already present in the repository and have only
been added to this reference.


Summary of changes:
 .../camel/catalog/docs/graphql-component.adoc      | 37 +++++++++++++-
 .../graphql/GraphqlEndpointConfigurer.java         | 12 +++++
 .../graphql/GraphqlEndpointUriFactory.java         | 12 +++--
 .../apache/camel/component/graphql/graphql.json    |  2 +
 .../src/main/docs/graphql-component.adoc           | 37 +++++++++++++-
 .../camel/component/graphql/GraphqlEndpoint.java   | 33 +++++++++++++
 .../camel/component/graphql/GraphqlProducer.java   | 29 ++++++++++-
 .../component/graphql/GraphqlComponentTest.java    | 56 ++++++++++++++++++++++
 .../dsl/GraphqlEndpointBuilderFactory.java         | 29 +++++++++++
 .../modules/ROOT/pages/graphql-component.adoc      | 37 +++++++++++++-
 10 files changed, 271 insertions(+), 13 deletions(-)

[camel] 02/02: CAMEL-16122: camel-graphql - Supply query via body or header.

Posted by je...@apache.org.
This is an automated email from the ASF dual-hosted git repository.

jeremyross pushed a commit to branch main
in repository https://gitbox.apache.org/repos/asf/camel.git

commit ff3021530e337e2311a29eec27dddb3f98f37b7f
Author: Jeremy Ross <je...@gmail.com>
AuthorDate: Mon Aug 16 10:06:33 2021 -0500

    CAMEL-16122: camel-graphql - Supply query via body or header.
---
 .../camel/catalog/docs/graphql-component.adoc      | 23 +++++++++++++++--
 .../graphql/GraphqlEndpointConfigurer.java         |  6 +++++
 .../graphql/GraphqlEndpointUriFactory.java         | 11 ++++----
 .../apache/camel/component/graphql/graphql.json    |  1 +
 .../src/main/docs/graphql-component.adoc           | 23 +++++++++++++++--
 .../camel/component/graphql/GraphqlEndpoint.java   | 21 ++++++++++++++++
 .../camel/component/graphql/GraphqlProducer.java   | 15 ++++++++++-
 .../component/graphql/GraphqlComponentTest.java    | 29 ++++++++++++++++++++++
 .../dsl/GraphqlEndpointBuilderFactory.java         | 14 +++++++++++
 .../modules/ROOT/pages/graphql-component.adoc      | 23 +++++++++++++++--
 10 files changed, 154 insertions(+), 12 deletions(-)

diff --git a/catalog/camel-catalog/src/generated/resources/org/apache/camel/catalog/docs/graphql-component.adoc b/catalog/camel-catalog/src/generated/resources/org/apache/camel/catalog/docs/graphql-component.adoc
index 289f573..2cce5bd 100644
--- a/catalog/camel-catalog/src/generated/resources/org/apache/camel/catalog/docs/graphql-component.adoc
+++ b/catalog/camel-catalog/src/generated/resources/org/apache/camel/catalog/docs/graphql-component.adoc
@@ -100,7 +100,7 @@ with the following path and query parameters:
 |===
 
 
-=== Query Parameters (11 parameters):
+=== Query Parameters (12 parameters):
 
 
 [width="100%",cols="2,5,^1,2",options="header"]
@@ -111,6 +111,7 @@ with the following path and query parameters:
 | *proxyHost* (producer) | The proxy host in the format hostname:port. |  | String
 | *query* (producer) | The query text. |  | String
 | *queryFile* (producer) | The query file name located in the classpath. |  | String
+| *queryHeader* (producer) | The name of a header containing the GraphQL query. |  | String
 | *variables* (producer) | The JsonObject instance containing the operation variables. |  | JsonObject
 | *variablesHeader* (producer) | The name of a header containing a JsonObject instance containing the operation variables. |  | String
 | *accessToken* (security) | The access token sent in the Authorization header. |  | String
@@ -123,7 +124,7 @@ with the following path and query parameters:
 
 == Message Body
 
-If the `variables` and `variablesHeader` parameters are not used and the IN body is a JsonObject instance, Camel will use it for the operation's variables. Camel will store the GraphQL response from the external server on the OUT message body. All headers from the IN message will be copied to the OUT message, so headers are preserved during routing. Additionally Camel will add the HTTP response headers as well to the OUT message headers.
+If the `variables` and `variablesHeader` parameters are not set and the IN body is a JsonObject instance, Camel will use it for the operation's variables. If the `query` and `queryFile` parameters are not set and the IN body is a String, Camel will use it as the query. Camel will store the GraphQL response from the external server on the OUT message body. All headers from the IN message will be copied to the OUT message, so headers are preserved during routing. Additionally Camel will ad [...]
 
 == Examples
 
@@ -137,6 +138,24 @@ from("direct:start")
     .to("graphql://http://example.com/graphql?query={books{id name}}")
 ----
 
+The body can also be used for the query:
+
+[source,java]
+----
+from("direct:start")
+    .setBody(constant("{books{id name}}"))
+    .to("graphql://http://example.com/graphql")
+----
+
+The query can come from a header also:
+
+[source,java]
+----
+from("direct:start")
+    .setHeader("myQuery", constant("{books{id name}}"))
+    .to("graphql://http://example.com/graphql?queryHeader=myQuery")
+----
+
 More complex queries can be stored in a file and referenced in the URI:
 
 booksQuery.graphql file:
diff --git a/components/camel-graphql/src/generated/java/org/apache/camel/component/graphql/GraphqlEndpointConfigurer.java b/components/camel-graphql/src/generated/java/org/apache/camel/component/graphql/GraphqlEndpointConfigurer.java
index 13d6e61..c804a93 100644
--- a/components/camel-graphql/src/generated/java/org/apache/camel/component/graphql/GraphqlEndpointConfigurer.java
+++ b/components/camel-graphql/src/generated/java/org/apache/camel/component/graphql/GraphqlEndpointConfigurer.java
@@ -35,6 +35,8 @@ public class GraphqlEndpointConfigurer extends PropertyConfigurerSupport impleme
         case "query": target.setQuery(property(camelContext, java.lang.String.class, value)); return true;
         case "queryfile":
         case "queryFile": target.setQueryFile(property(camelContext, java.lang.String.class, value)); return true;
+        case "queryheader":
+        case "queryHeader": target.setQueryHeader(property(camelContext, java.lang.String.class, value)); return true;
         case "username": target.setUsername(property(camelContext, java.lang.String.class, value)); return true;
         case "variables": target.setVariables(property(camelContext, org.apache.camel.util.json.JsonObject.class, value)); return true;
         case "variablesheader":
@@ -60,6 +62,8 @@ public class GraphqlEndpointConfigurer extends PropertyConfigurerSupport impleme
         case "query": return java.lang.String.class;
         case "queryfile":
         case "queryFile": return java.lang.String.class;
+        case "queryheader":
+        case "queryHeader": return java.lang.String.class;
         case "username": return java.lang.String.class;
         case "variables": return org.apache.camel.util.json.JsonObject.class;
         case "variablesheader":
@@ -86,6 +90,8 @@ public class GraphqlEndpointConfigurer extends PropertyConfigurerSupport impleme
         case "query": return target.getQuery();
         case "queryfile":
         case "queryFile": return target.getQueryFile();
+        case "queryheader":
+        case "queryHeader": return target.getQueryHeader();
         case "username": return target.getUsername();
         case "variables": return target.getVariables();
         case "variablesheader":
diff --git a/components/camel-graphql/src/generated/java/org/apache/camel/component/graphql/GraphqlEndpointUriFactory.java b/components/camel-graphql/src/generated/java/org/apache/camel/component/graphql/GraphqlEndpointUriFactory.java
index b7d8a1c..57312bf 100644
--- a/components/camel-graphql/src/generated/java/org/apache/camel/component/graphql/GraphqlEndpointUriFactory.java
+++ b/components/camel-graphql/src/generated/java/org/apache/camel/component/graphql/GraphqlEndpointUriFactory.java
@@ -20,18 +20,19 @@ public class GraphqlEndpointUriFactory extends org.apache.camel.support.componen
     private static final Set<String> PROPERTY_NAMES;
     private static final Set<String> SECRET_PROPERTY_NAMES;
     static {
-        Set<String> props = new HashSet<>(12);
-        props.add("lazyStartProducer");
+        Set<String> props = new HashSet<>(13);
+        props.add("queryHeader");
         props.add("queryFile");
         props.add("variables");
-        props.add("password");
-        props.add("jwtAuthorizationType");
-        props.add("httpUri");
         props.add("query");
         props.add("variablesHeader");
         props.add("operationName");
         props.add("accessToken");
         props.add("proxyHost");
+        props.add("lazyStartProducer");
+        props.add("password");
+        props.add("jwtAuthorizationType");
+        props.add("httpUri");
         props.add("username");
         PROPERTY_NAMES = Collections.unmodifiableSet(props);
         Set<String> secretProps = new HashSet<>(3);
diff --git a/components/camel-graphql/src/generated/resources/org/apache/camel/component/graphql/graphql.json b/components/camel-graphql/src/generated/resources/org/apache/camel/component/graphql/graphql.json
index 93bff64..89b6011 100644
--- a/components/camel-graphql/src/generated/resources/org/apache/camel/component/graphql/graphql.json
+++ b/components/camel-graphql/src/generated/resources/org/apache/camel/component/graphql/graphql.json
@@ -32,6 +32,7 @@
     "proxyHost": { "kind": "parameter", "displayName": "Proxy Host", "group": "producer", "label": "", "required": false, "type": "string", "javaType": "java.lang.String", "deprecated": false, "autowired": false, "secret": false, "description": "The proxy host in the format hostname:port." },
     "query": { "kind": "parameter", "displayName": "Query", "group": "producer", "label": "", "required": false, "type": "string", "javaType": "java.lang.String", "deprecated": false, "autowired": false, "secret": false, "description": "The query text." },
     "queryFile": { "kind": "parameter", "displayName": "Query File", "group": "producer", "label": "", "required": false, "type": "string", "javaType": "java.lang.String", "deprecated": false, "autowired": false, "secret": false, "description": "The query file name located in the classpath." },
+    "queryHeader": { "kind": "parameter", "displayName": "Query Header", "group": "producer", "label": "", "required": false, "type": "string", "javaType": "java.lang.String", "deprecated": false, "autowired": false, "secret": false, "description": "The name of a header containing the GraphQL query." },
     "variables": { "kind": "parameter", "displayName": "Variables", "group": "producer", "label": "", "required": false, "type": "object", "javaType": "org.apache.camel.util.json.JsonObject", "deprecated": false, "autowired": false, "secret": false, "description": "The JsonObject instance containing the operation variables." },
     "variablesHeader": { "kind": "parameter", "displayName": "Variables Header", "group": "producer", "label": "", "required": false, "type": "string", "javaType": "java.lang.String", "deprecated": false, "autowired": false, "secret": false, "description": "The name of a header containing a JsonObject instance containing the operation variables." },
     "accessToken": { "kind": "parameter", "displayName": "Access Token", "group": "security", "label": "security", "required": false, "type": "string", "javaType": "java.lang.String", "deprecated": false, "autowired": false, "secret": true, "description": "The access token sent in the Authorization header." },
diff --git a/components/camel-graphql/src/main/docs/graphql-component.adoc b/components/camel-graphql/src/main/docs/graphql-component.adoc
index 289f573..2cce5bd 100644
--- a/components/camel-graphql/src/main/docs/graphql-component.adoc
+++ b/components/camel-graphql/src/main/docs/graphql-component.adoc
@@ -100,7 +100,7 @@ with the following path and query parameters:
 |===
 
 
-=== Query Parameters (11 parameters):
+=== Query Parameters (12 parameters):
 
 
 [width="100%",cols="2,5,^1,2",options="header"]
@@ -111,6 +111,7 @@ with the following path and query parameters:
 | *proxyHost* (producer) | The proxy host in the format hostname:port. |  | String
 | *query* (producer) | The query text. |  | String
 | *queryFile* (producer) | The query file name located in the classpath. |  | String
+| *queryHeader* (producer) | The name of a header containing the GraphQL query. |  | String
 | *variables* (producer) | The JsonObject instance containing the operation variables. |  | JsonObject
 | *variablesHeader* (producer) | The name of a header containing a JsonObject instance containing the operation variables. |  | String
 | *accessToken* (security) | The access token sent in the Authorization header. |  | String
@@ -123,7 +124,7 @@ with the following path and query parameters:
 
 == Message Body
 
-If the `variables` and `variablesHeader` parameters are not used and the IN body is a JsonObject instance, Camel will use it for the operation's variables. Camel will store the GraphQL response from the external server on the OUT message body. All headers from the IN message will be copied to the OUT message, so headers are preserved during routing. Additionally Camel will add the HTTP response headers as well to the OUT message headers.
+If the `variables` and `variablesHeader` parameters are not set and the IN body is a JsonObject instance, Camel will use it for the operation's variables. If the `query` and `queryFile` parameters are not set and the IN body is a String, Camel will use it as the query. Camel will store the GraphQL response from the external server on the OUT message body. All headers from the IN message will be copied to the OUT message, so headers are preserved during routing. Additionally Camel will ad [...]
 
 == Examples
 
@@ -137,6 +138,24 @@ from("direct:start")
     .to("graphql://http://example.com/graphql?query={books{id name}}")
 ----
 
+The body can also be used for the query:
+
+[source,java]
+----
+from("direct:start")
+    .setBody(constant("{books{id name}}"))
+    .to("graphql://http://example.com/graphql")
+----
+
+The query can come from a header also:
+
+[source,java]
+----
+from("direct:start")
+    .setHeader("myQuery", constant("{books{id name}}"))
+    .to("graphql://http://example.com/graphql?queryHeader=myQuery")
+----
+
 More complex queries can be stored in a file and referenced in the URI:
 
 booksQuery.graphql file:
diff --git a/components/camel-graphql/src/main/java/org/apache/camel/component/graphql/GraphqlEndpoint.java b/components/camel-graphql/src/main/java/org/apache/camel/component/graphql/GraphqlEndpoint.java
index d4b79b9..54bcc28 100644
--- a/components/camel-graphql/src/main/java/org/apache/camel/component/graphql/GraphqlEndpoint.java
+++ b/components/camel-graphql/src/main/java/org/apache/camel/component/graphql/GraphqlEndpoint.java
@@ -76,6 +76,8 @@ public class GraphqlEndpoint extends DefaultEndpoint {
     private JsonObject variables;
     @UriParam
     private String variablesHeader;
+    @UriParam
+    private String queryHeader;
 
     private CloseableHttpClient httpClient;
 
@@ -256,4 +258,23 @@ public class GraphqlEndpoint extends DefaultEndpoint {
     public void setVariablesHeader(String variablesHeader) {
         this.variablesHeader = variablesHeader;
     }
+
+    public String getQueryHeader() {
+        return queryHeader;
+    }
+
+    /**
+     * The name of a header containing the GraphQL query.
+     */
+    public void setQueryHeader(String queryHeader) {
+        this.queryHeader = queryHeader;
+    }
+
+    public CloseableHttpClient getHttpClient() {
+        return httpClient;
+    }
+
+    public void setHttpClient(CloseableHttpClient httpClient) {
+        this.httpClient = httpClient;
+    }
 }
diff --git a/components/camel-graphql/src/main/java/org/apache/camel/component/graphql/GraphqlProducer.java b/components/camel-graphql/src/main/java/org/apache/camel/component/graphql/GraphqlProducer.java
index 4b38424..9478bab 100644
--- a/components/camel-graphql/src/main/java/org/apache/camel/component/graphql/GraphqlProducer.java
+++ b/components/camel-graphql/src/main/java/org/apache/camel/component/graphql/GraphqlProducer.java
@@ -20,6 +20,7 @@ import java.net.URI;
 
 import org.apache.camel.AsyncCallback;
 import org.apache.camel.Exchange;
+import org.apache.camel.InvalidPayloadException;
 import org.apache.camel.support.DefaultAsyncProducer;
 import org.apache.camel.util.json.JsonObject;
 import org.apache.http.HttpEntity;
@@ -46,7 +47,7 @@ public class GraphqlProducer extends DefaultAsyncProducer {
         try {
             CloseableHttpClient httpClient = getEndpoint().getHttpclient();
             URI httpUri = getEndpoint().getHttpUri();
-            String requestBody = buildRequestBody(getEndpoint().getQuery(), getEndpoint().getOperationName(),
+            String requestBody = buildRequestBody(getQuery(exchange), getEndpoint().getOperationName(),
                     getVariables(exchange));
             HttpEntity requestEntity = new StringEntity(requestBody, ContentType.create("application/json", "UTF-8"));
 
@@ -75,6 +76,18 @@ public class GraphqlProducer extends DefaultAsyncProducer {
         return jsonObject.toJson();
     }
 
+    private String getQuery(Exchange exchange) throws InvalidPayloadException {
+        String query = null;
+        if (getEndpoint().getQuery() != null) {
+            query = getEndpoint().getQuery();
+        } else if (getEndpoint().getQueryHeader() != null) {
+            query = exchange.getIn().getHeader(getEndpoint().getQueryHeader(), String.class);
+        } else {
+            query = exchange.getIn().getMandatoryBody(String.class);
+        }
+        return query;
+    }
+
     private JsonObject getVariables(Exchange exchange) {
         JsonObject variables = null;
         if (getEndpoint().getVariables() != null) {
diff --git a/components/camel-graphql/src/test/java/org/apache/camel/component/graphql/GraphqlComponentTest.java b/components/camel-graphql/src/test/java/org/apache/camel/component/graphql/GraphqlComponentTest.java
index b2cd7b3..356f178 100644
--- a/components/camel-graphql/src/test/java/org/apache/camel/component/graphql/GraphqlComponentTest.java
+++ b/components/camel-graphql/src/test/java/org/apache/camel/component/graphql/GraphqlComponentTest.java
@@ -103,6 +103,15 @@ public class GraphqlComponentTest extends CamelTestSupport {
                         .to("graphql://http://localhost:" + server.getPort()
                             + "/graphql?query={books{id name}}&variablesHeader=bookByIdQueryVariables")
                         .to("mock:result");
+                from("direct:start6")
+                        .to("graphql://http://localhost:" + server.getPort()
+                            + "/graphql")
+                        .to("mock:result");
+                from("direct:start7")
+                        .setHeader("myQuery", constant("{books{id name}}"))
+                        .to("graphql://http://localhost:" + server.getPort()
+                            + "/graphql?queryHeader=myQuery")
+                        .to("mock:result");
             }
         };
     }
@@ -118,6 +127,26 @@ public class GraphqlComponentTest extends CamelTestSupport {
     }
 
     @Test
+    public void booksQueryWithStaticQueryInBody() throws Exception {
+        result.expectedMessageCount(1);
+        result.expectedBodiesReceived(booksQueryResult);
+
+        template.sendBody("direct:start6", "{books{id name}}");
+
+        result.assertIsSatisfied();
+    }
+
+    @Test
+    public void booksQueryWithStaticQueryInHeader() throws Exception {
+        result.expectedMessageCount(1);
+        result.expectedBodiesReceived(booksQueryResult);
+
+        template.sendBody("direct:start7", "");
+
+        result.assertIsSatisfied();
+    }
+
+    @Test
     public void booksQueryWithQueryFile() throws Exception {
         result.expectedMessageCount(1);
         result.expectedBodiesReceived(booksQueryResult);
diff --git a/core/camel-endpointdsl/src/generated/java/org/apache/camel/builder/endpoint/dsl/GraphqlEndpointBuilderFactory.java b/core/camel-endpointdsl/src/generated/java/org/apache/camel/builder/endpoint/dsl/GraphqlEndpointBuilderFactory.java
index ef65cac..9866d90 100644
--- a/core/camel-endpointdsl/src/generated/java/org/apache/camel/builder/endpoint/dsl/GraphqlEndpointBuilderFactory.java
+++ b/core/camel-endpointdsl/src/generated/java/org/apache/camel/builder/endpoint/dsl/GraphqlEndpointBuilderFactory.java
@@ -140,6 +140,20 @@ public interface GraphqlEndpointBuilderFactory {
             return this;
         }
         /**
+         * The name of a header containing the GraphQL query.
+         * 
+         * The option is a: &lt;code&gt;java.lang.String&lt;/code&gt; type.
+         * 
+         * Group: producer
+         * 
+         * @param queryHeader the value to set
+         * @return the dsl builder
+         */
+        default GraphqlEndpointBuilder queryHeader(String queryHeader) {
+            doSetProperty("queryHeader", queryHeader);
+            return this;
+        }
+        /**
          * The JsonObject instance containing the operation variables.
          * 
          * The option is a:
diff --git a/docs/components/modules/ROOT/pages/graphql-component.adoc b/docs/components/modules/ROOT/pages/graphql-component.adoc
index d88fd05..1aec52f 100644
--- a/docs/components/modules/ROOT/pages/graphql-component.adoc
+++ b/docs/components/modules/ROOT/pages/graphql-component.adoc
@@ -102,7 +102,7 @@ with the following path and query parameters:
 |===
 
 
-=== Query Parameters (11 parameters):
+=== Query Parameters (12 parameters):
 
 
 [width="100%",cols="2,5,^1,2",options="header"]
@@ -113,6 +113,7 @@ with the following path and query parameters:
 | *proxyHost* (producer) | The proxy host in the format hostname:port. |  | String
 | *query* (producer) | The query text. |  | String
 | *queryFile* (producer) | The query file name located in the classpath. |  | String
+| *queryHeader* (producer) | The name of a header containing the GraphQL query. |  | String
 | *variables* (producer) | The JsonObject instance containing the operation variables. |  | JsonObject
 | *variablesHeader* (producer) | The name of a header containing a JsonObject instance containing the operation variables. |  | String
 | *accessToken* (security) | The access token sent in the Authorization header. |  | String
@@ -125,7 +126,7 @@ with the following path and query parameters:
 
 == Message Body
 
-If the `variables` and `variablesHeader` parameters are not used and the IN body is a JsonObject instance, Camel will use it for the operation's variables. Camel will store the GraphQL response from the external server on the OUT message body. All headers from the IN message will be copied to the OUT message, so headers are preserved during routing. Additionally Camel will add the HTTP response headers as well to the OUT message headers.
+If the `variables` and `variablesHeader` parameters are not set and the IN body is a JsonObject instance, Camel will use it for the operation's variables. If the `query` and `queryFile` parameters are not set and the IN body is a String, Camel will use it as the query. Camel will store the GraphQL response from the external server on the OUT message body. All headers from the IN message will be copied to the OUT message, so headers are preserved during routing. Additionally Camel will ad [...]
 
 == Examples
 
@@ -139,6 +140,24 @@ from("direct:start")
     .to("graphql://http://example.com/graphql?query={books{id name}}")
 ----
 
+The body can also be used for the query:
+
+[source,java]
+----
+from("direct:start")
+    .setBody(constant("{books{id name}}"))
+    .to("graphql://http://example.com/graphql")
+----
+
+The query can come from a header also:
+
+[source,java]
+----
+from("direct:start")
+    .setHeader("myQuery", constant("{books{id name}}"))
+    .to("graphql://http://example.com/graphql?queryHeader=myQuery")
+----
+
 More complex queries can be stored in a file and referenced in the URI:
 
 booksQuery.graphql file:

[camel] 01/02: CAMEL-15864: camel-graphql - Supply variables in header or body.

Posted by je...@apache.org.
This is an automated email from the ASF dual-hosted git repository.

jeremyross pushed a commit to branch main
in repository https://gitbox.apache.org/repos/asf/camel.git

commit dff5afbeee7f9fa6c85fad899837ae3272704736
Author: Jeremy Ross <je...@gmail.com>
AuthorDate: Mon Aug 16 09:24:40 2021 -0500

    CAMEL-15864: camel-graphql - Supply variables in header or body.
---
 .../camel/catalog/docs/graphql-component.adoc      | 18 +++++++++++++--
 .../graphql/GraphqlEndpointConfigurer.java         |  6 +++++
 .../graphql/GraphqlEndpointUriFactory.java         |  3 ++-
 .../apache/camel/component/graphql/graphql.json    |  1 +
 .../src/main/docs/graphql-component.adoc           | 18 +++++++++++++--
 .../camel/component/graphql/GraphqlEndpoint.java   | 12 ++++++++++
 .../camel/component/graphql/GraphqlProducer.java   | 14 ++++++++++-
 .../component/graphql/GraphqlComponentTest.java    | 27 ++++++++++++++++++++++
 .../dsl/GraphqlEndpointBuilderFactory.java         | 15 ++++++++++++
 .../modules/ROOT/pages/graphql-component.adoc      | 18 +++++++++++++--
 10 files changed, 124 insertions(+), 8 deletions(-)

diff --git a/catalog/camel-catalog/src/generated/resources/org/apache/camel/catalog/docs/graphql-component.adoc b/catalog/camel-catalog/src/generated/resources/org/apache/camel/catalog/docs/graphql-component.adoc
index 8a1e1a4..289f573 100644
--- a/catalog/camel-catalog/src/generated/resources/org/apache/camel/catalog/docs/graphql-component.adoc
+++ b/catalog/camel-catalog/src/generated/resources/org/apache/camel/catalog/docs/graphql-component.adoc
@@ -100,7 +100,7 @@ with the following path and query parameters:
 |===
 
 
-=== Query Parameters (10 parameters):
+=== Query Parameters (11 parameters):
 
 
 [width="100%",cols="2,5,^1,2",options="header"]
@@ -112,6 +112,7 @@ with the following path and query parameters:
 | *query* (producer) | The query text. |  | String
 | *queryFile* (producer) | The query file name located in the classpath. |  | String
 | *variables* (producer) | The JsonObject instance containing the operation variables. |  | JsonObject
+| *variablesHeader* (producer) | The name of a header containing a JsonObject instance containing the operation variables. |  | String
 | *accessToken* (security) | The access token sent in the Authorization header. |  | String
 | *jwtAuthorizationType* (security) | The JWT Authorization type. Default is Bearer. | Bearer | String
 | *password* (security) | The password for Basic authentication. |  | String
@@ -122,7 +123,7 @@ with the following path and query parameters:
 
 == Message Body
 
-Camel will store the GraphQL response from the external server on the OUT message body. All headers from the IN message will be copied to the OUT message, so headers are preserved during routing. Additionally Camel will add the HTTP response headers as well to the OUT message headers.
+If the `variables` and `variablesHeader` parameters are not used and the IN body is a JsonObject instance, Camel will use it for the operation's variables. Camel will store the GraphQL response from the external server on the OUT message body. All headers from the IN message will be copied to the OUT message, so headers are preserved during routing. Additionally Camel will add the HTTP response headers as well to the OUT message headers.
 
 == Examples
 
@@ -177,6 +178,19 @@ from("direct:start")
     .to("graphql://http://example.com/graphql?queryFile=bookByIdQuery.graphql&variables=#bookByIdQueryVariables")
 ----
 
+A query that accesses variables via the variablesHeader parameter:
+
+[source,java]
+----
+from("direct:start")
+    .setHeader("myVariables", () -> {
+        JsonObject variables = new JsonObject();
+        variables.put("id", "book-1");
+        return variables;
+    })
+    .to("graphql://http://example.com/graphql?queryFile=bookByIdQuery.graphql&variablesHeader=myVariables")
+----
+
 === Mutations
 
 Mutations are like queries with variables. They specify a query and a reference to a variables bean:
diff --git a/components/camel-graphql/src/generated/java/org/apache/camel/component/graphql/GraphqlEndpointConfigurer.java b/components/camel-graphql/src/generated/java/org/apache/camel/component/graphql/GraphqlEndpointConfigurer.java
index 93da2da..13d6e61 100644
--- a/components/camel-graphql/src/generated/java/org/apache/camel/component/graphql/GraphqlEndpointConfigurer.java
+++ b/components/camel-graphql/src/generated/java/org/apache/camel/component/graphql/GraphqlEndpointConfigurer.java
@@ -37,6 +37,8 @@ public class GraphqlEndpointConfigurer extends PropertyConfigurerSupport impleme
         case "queryFile": target.setQueryFile(property(camelContext, java.lang.String.class, value)); return true;
         case "username": target.setUsername(property(camelContext, java.lang.String.class, value)); return true;
         case "variables": target.setVariables(property(camelContext, org.apache.camel.util.json.JsonObject.class, value)); return true;
+        case "variablesheader":
+        case "variablesHeader": target.setVariablesHeader(property(camelContext, java.lang.String.class, value)); return true;
         default: return false;
         }
     }
@@ -60,6 +62,8 @@ public class GraphqlEndpointConfigurer extends PropertyConfigurerSupport impleme
         case "queryFile": return java.lang.String.class;
         case "username": return java.lang.String.class;
         case "variables": return org.apache.camel.util.json.JsonObject.class;
+        case "variablesheader":
+        case "variablesHeader": return java.lang.String.class;
         default: return null;
         }
     }
@@ -84,6 +88,8 @@ public class GraphqlEndpointConfigurer extends PropertyConfigurerSupport impleme
         case "queryFile": return target.getQueryFile();
         case "username": return target.getUsername();
         case "variables": return target.getVariables();
+        case "variablesheader":
+        case "variablesHeader": return target.getVariablesHeader();
         default: return null;
         }
     }
diff --git a/components/camel-graphql/src/generated/java/org/apache/camel/component/graphql/GraphqlEndpointUriFactory.java b/components/camel-graphql/src/generated/java/org/apache/camel/component/graphql/GraphqlEndpointUriFactory.java
index 3379db5..b7d8a1c 100644
--- a/components/camel-graphql/src/generated/java/org/apache/camel/component/graphql/GraphqlEndpointUriFactory.java
+++ b/components/camel-graphql/src/generated/java/org/apache/camel/component/graphql/GraphqlEndpointUriFactory.java
@@ -20,7 +20,7 @@ public class GraphqlEndpointUriFactory extends org.apache.camel.support.componen
     private static final Set<String> PROPERTY_NAMES;
     private static final Set<String> SECRET_PROPERTY_NAMES;
     static {
-        Set<String> props = new HashSet<>(11);
+        Set<String> props = new HashSet<>(12);
         props.add("lazyStartProducer");
         props.add("queryFile");
         props.add("variables");
@@ -28,6 +28,7 @@ public class GraphqlEndpointUriFactory extends org.apache.camel.support.componen
         props.add("jwtAuthorizationType");
         props.add("httpUri");
         props.add("query");
+        props.add("variablesHeader");
         props.add("operationName");
         props.add("accessToken");
         props.add("proxyHost");
diff --git a/components/camel-graphql/src/generated/resources/org/apache/camel/component/graphql/graphql.json b/components/camel-graphql/src/generated/resources/org/apache/camel/component/graphql/graphql.json
index d02a6fa..93bff64 100644
--- a/components/camel-graphql/src/generated/resources/org/apache/camel/component/graphql/graphql.json
+++ b/components/camel-graphql/src/generated/resources/org/apache/camel/component/graphql/graphql.json
@@ -33,6 +33,7 @@
     "query": { "kind": "parameter", "displayName": "Query", "group": "producer", "label": "", "required": false, "type": "string", "javaType": "java.lang.String", "deprecated": false, "autowired": false, "secret": false, "description": "The query text." },
     "queryFile": { "kind": "parameter", "displayName": "Query File", "group": "producer", "label": "", "required": false, "type": "string", "javaType": "java.lang.String", "deprecated": false, "autowired": false, "secret": false, "description": "The query file name located in the classpath." },
     "variables": { "kind": "parameter", "displayName": "Variables", "group": "producer", "label": "", "required": false, "type": "object", "javaType": "org.apache.camel.util.json.JsonObject", "deprecated": false, "autowired": false, "secret": false, "description": "The JsonObject instance containing the operation variables." },
+    "variablesHeader": { "kind": "parameter", "displayName": "Variables Header", "group": "producer", "label": "", "required": false, "type": "string", "javaType": "java.lang.String", "deprecated": false, "autowired": false, "secret": false, "description": "The name of a header containing a JsonObject instance containing the operation variables." },
     "accessToken": { "kind": "parameter", "displayName": "Access Token", "group": "security", "label": "security", "required": false, "type": "string", "javaType": "java.lang.String", "deprecated": false, "autowired": false, "secret": true, "description": "The access token sent in the Authorization header." },
     "jwtAuthorizationType": { "kind": "parameter", "displayName": "Jwt Authorization Type", "group": "security", "label": "security", "required": false, "type": "string", "javaType": "java.lang.String", "deprecated": false, "autowired": false, "secret": false, "defaultValue": "Bearer", "description": "The JWT Authorization type. Default is Bearer." },
     "password": { "kind": "parameter", "displayName": "Password", "group": "security", "label": "security", "required": false, "type": "string", "javaType": "java.lang.String", "deprecated": false, "autowired": false, "secret": true, "description": "The password for Basic authentication." },
diff --git a/components/camel-graphql/src/main/docs/graphql-component.adoc b/components/camel-graphql/src/main/docs/graphql-component.adoc
index 8a1e1a4..289f573 100644
--- a/components/camel-graphql/src/main/docs/graphql-component.adoc
+++ b/components/camel-graphql/src/main/docs/graphql-component.adoc
@@ -100,7 +100,7 @@ with the following path and query parameters:
 |===
 
 
-=== Query Parameters (10 parameters):
+=== Query Parameters (11 parameters):
 
 
 [width="100%",cols="2,5,^1,2",options="header"]
@@ -112,6 +112,7 @@ with the following path and query parameters:
 | *query* (producer) | The query text. |  | String
 | *queryFile* (producer) | The query file name located in the classpath. |  | String
 | *variables* (producer) | The JsonObject instance containing the operation variables. |  | JsonObject
+| *variablesHeader* (producer) | The name of a header containing a JsonObject instance containing the operation variables. |  | String
 | *accessToken* (security) | The access token sent in the Authorization header. |  | String
 | *jwtAuthorizationType* (security) | The JWT Authorization type. Default is Bearer. | Bearer | String
 | *password* (security) | The password for Basic authentication. |  | String
@@ -122,7 +123,7 @@ with the following path and query parameters:
 
 == Message Body
 
-Camel will store the GraphQL response from the external server on the OUT message body. All headers from the IN message will be copied to the OUT message, so headers are preserved during routing. Additionally Camel will add the HTTP response headers as well to the OUT message headers.
+If the `variables` and `variablesHeader` parameters are not used and the IN body is a JsonObject instance, Camel will use it for the operation's variables. Camel will store the GraphQL response from the external server on the OUT message body. All headers from the IN message will be copied to the OUT message, so headers are preserved during routing. Additionally Camel will add the HTTP response headers as well to the OUT message headers.
 
 == Examples
 
@@ -177,6 +178,19 @@ from("direct:start")
     .to("graphql://http://example.com/graphql?queryFile=bookByIdQuery.graphql&variables=#bookByIdQueryVariables")
 ----
 
+A query that accesses variables via the variablesHeader parameter:
+
+[source,java]
+----
+from("direct:start")
+    .setHeader("myVariables", () -> {
+        JsonObject variables = new JsonObject();
+        variables.put("id", "book-1");
+        return variables;
+    })
+    .to("graphql://http://example.com/graphql?queryFile=bookByIdQuery.graphql&variablesHeader=myVariables")
+----
+
 === Mutations
 
 Mutations are like queries with variables. They specify a query and a reference to a variables bean:
diff --git a/components/camel-graphql/src/main/java/org/apache/camel/component/graphql/GraphqlEndpoint.java b/components/camel-graphql/src/main/java/org/apache/camel/component/graphql/GraphqlEndpoint.java
index 202baff..d4b79b9 100644
--- a/components/camel-graphql/src/main/java/org/apache/camel/component/graphql/GraphqlEndpoint.java
+++ b/components/camel-graphql/src/main/java/org/apache/camel/component/graphql/GraphqlEndpoint.java
@@ -74,6 +74,8 @@ public class GraphqlEndpoint extends DefaultEndpoint {
     private String operationName;
     @UriParam
     private JsonObject variables;
+    @UriParam
+    private String variablesHeader;
 
     private CloseableHttpClient httpClient;
 
@@ -244,4 +246,14 @@ public class GraphqlEndpoint extends DefaultEndpoint {
         this.variables = variables;
     }
 
+    public String getVariablesHeader() {
+        return variablesHeader;
+    }
+
+    /**
+     * The name of a header containing a JsonObject instance containing the operation variables.
+     */
+    public void setVariablesHeader(String variablesHeader) {
+        this.variablesHeader = variablesHeader;
+    }
 }
diff --git a/components/camel-graphql/src/main/java/org/apache/camel/component/graphql/GraphqlProducer.java b/components/camel-graphql/src/main/java/org/apache/camel/component/graphql/GraphqlProducer.java
index a74e40b..4b38424 100644
--- a/components/camel-graphql/src/main/java/org/apache/camel/component/graphql/GraphqlProducer.java
+++ b/components/camel-graphql/src/main/java/org/apache/camel/component/graphql/GraphqlProducer.java
@@ -47,7 +47,7 @@ public class GraphqlProducer extends DefaultAsyncProducer {
             CloseableHttpClient httpClient = getEndpoint().getHttpclient();
             URI httpUri = getEndpoint().getHttpUri();
             String requestBody = buildRequestBody(getEndpoint().getQuery(), getEndpoint().getOperationName(),
-                    getEndpoint().getVariables());
+                    getVariables(exchange));
             HttpEntity requestEntity = new StringEntity(requestBody, ContentType.create("application/json", "UTF-8"));
 
             HttpPost httpPost = new HttpPost(httpUri);
@@ -74,4 +74,16 @@ public class GraphqlProducer extends DefaultAsyncProducer {
         jsonObject.put("variables", variables != null ? variables : new JsonObject());
         return jsonObject.toJson();
     }
+
+    private JsonObject getVariables(Exchange exchange) {
+        JsonObject variables = null;
+        if (getEndpoint().getVariables() != null) {
+            variables = getEndpoint().getVariables();
+        } else if (getEndpoint().getVariablesHeader() != null) {
+            variables = exchange.getIn().getHeader(getEndpoint().getVariablesHeader(), JsonObject.class);
+        } else if (exchange.getIn().getBody() instanceof JsonObject) {
+            variables = exchange.getIn().getBody(JsonObject.class);
+        }
+        return variables;
+    }
 }
diff --git a/components/camel-graphql/src/test/java/org/apache/camel/component/graphql/GraphqlComponentTest.java b/components/camel-graphql/src/test/java/org/apache/camel/component/graphql/GraphqlComponentTest.java
index 26b04f2..b2cd7b3 100644
--- a/components/camel-graphql/src/test/java/org/apache/camel/component/graphql/GraphqlComponentTest.java
+++ b/components/camel-graphql/src/test/java/org/apache/camel/component/graphql/GraphqlComponentTest.java
@@ -99,6 +99,10 @@ public class GraphqlComponentTest extends CamelTestSupport {
                         .to("graphql://http://localhost:" + server.getPort()
                             + "/graphql?queryFile=addBookMutation.graphql&variables=#addBookMutationVariables")
                         .to("mock:result");
+                from("direct:start5")
+                        .to("graphql://http://localhost:" + server.getPort()
+                            + "/graphql?query={books{id name}}&variablesHeader=bookByIdQueryVariables")
+                        .to("mock:result");
             }
         };
     }
@@ -143,4 +147,27 @@ public class GraphqlComponentTest extends CamelTestSupport {
         result.assertIsSatisfied();
     }
 
+    @Test
+    public void booksQueryWithVariablesHeader() throws Exception {
+        result.expectedMessageCount(1);
+        result.expectedBodiesReceived(booksQueryResult);
+
+        JsonObject variables = new JsonObject();
+        variables.put("id", "book-1");
+        template.sendBodyAndHeader("direct:start5", "", "bookByIdQueryVariables", variables);
+
+        result.assertIsSatisfied();
+    }
+
+    @Test
+    public void booksQueryWithVariablesBody() throws Exception {
+        result.expectedMessageCount(1);
+        result.expectedBodiesReceived(booksQueryResult);
+
+        JsonObject variables = new JsonObject();
+        variables.put("id", "book-1");
+        template.sendBody("direct:start1", variables);
+
+        result.assertIsSatisfied();
+    }
 }
diff --git a/core/camel-endpointdsl/src/generated/java/org/apache/camel/builder/endpoint/dsl/GraphqlEndpointBuilderFactory.java b/core/camel-endpointdsl/src/generated/java/org/apache/camel/builder/endpoint/dsl/GraphqlEndpointBuilderFactory.java
index e5c5900..ef65cac 100644
--- a/core/camel-endpointdsl/src/generated/java/org/apache/camel/builder/endpoint/dsl/GraphqlEndpointBuilderFactory.java
+++ b/core/camel-endpointdsl/src/generated/java/org/apache/camel/builder/endpoint/dsl/GraphqlEndpointBuilderFactory.java
@@ -170,6 +170,21 @@ public interface GraphqlEndpointBuilderFactory {
             return this;
         }
         /**
+         * The name of a header containing a JsonObject instance containing the
+         * operation variables.
+         * 
+         * The option is a: &lt;code&gt;java.lang.String&lt;/code&gt; type.
+         * 
+         * Group: producer
+         * 
+         * @param variablesHeader the value to set
+         * @return the dsl builder
+         */
+        default GraphqlEndpointBuilder variablesHeader(String variablesHeader) {
+            doSetProperty("variablesHeader", variablesHeader);
+            return this;
+        }
+        /**
          * The access token sent in the Authorization header.
          * 
          * The option is a: &lt;code&gt;java.lang.String&lt;/code&gt; type.
diff --git a/docs/components/modules/ROOT/pages/graphql-component.adoc b/docs/components/modules/ROOT/pages/graphql-component.adoc
index d02cccb..d88fd05 100644
--- a/docs/components/modules/ROOT/pages/graphql-component.adoc
+++ b/docs/components/modules/ROOT/pages/graphql-component.adoc
@@ -102,7 +102,7 @@ with the following path and query parameters:
 |===
 
 
-=== Query Parameters (10 parameters):
+=== Query Parameters (11 parameters):
 
 
 [width="100%",cols="2,5,^1,2",options="header"]
@@ -114,6 +114,7 @@ with the following path and query parameters:
 | *query* (producer) | The query text. |  | String
 | *queryFile* (producer) | The query file name located in the classpath. |  | String
 | *variables* (producer) | The JsonObject instance containing the operation variables. |  | JsonObject
+| *variablesHeader* (producer) | The name of a header containing a JsonObject instance containing the operation variables. |  | String
 | *accessToken* (security) | The access token sent in the Authorization header. |  | String
 | *jwtAuthorizationType* (security) | The JWT Authorization type. Default is Bearer. | Bearer | String
 | *password* (security) | The password for Basic authentication. |  | String
@@ -124,7 +125,7 @@ with the following path and query parameters:
 
 == Message Body
 
-Camel will store the GraphQL response from the external server on the OUT message body. All headers from the IN message will be copied to the OUT message, so headers are preserved during routing. Additionally Camel will add the HTTP response headers as well to the OUT message headers.
+If the `variables` and `variablesHeader` parameters are not used and the IN body is a JsonObject instance, Camel will use it for the operation's variables. Camel will store the GraphQL response from the external server on the OUT message body. All headers from the IN message will be copied to the OUT message, so headers are preserved during routing. Additionally Camel will add the HTTP response headers as well to the OUT message headers.
 
 == Examples
 
@@ -179,6 +180,19 @@ from("direct:start")
     .to("graphql://http://example.com/graphql?queryFile=bookByIdQuery.graphql&variables=#bookByIdQueryVariables")
 ----
 
+A query that accesses variables via the variablesHeader parameter:
+
+[source,java]
+----
+from("direct:start")
+    .setHeader("myVariables", () -> {
+        JsonObject variables = new JsonObject();
+        variables.put("id", "book-1");
+        return variables;
+    })
+    .to("graphql://http://example.com/graphql?queryFile=bookByIdQuery.graphql&variablesHeader=myVariables")
+----
+
 === Mutations
 
 Mutations are like queries with variables. They specify a query and a reference to a variables bean: