How to pass variables at run time to graphql requests - jmeter

I am designing a Jmeter script which has graphQL type HTTP request.
One of the graphQL requests accepts a user defined type as an input parameter.
In Jmeter I created a graphQL type HTTP request. In the query section I added the query and in the variables section I added the variable.
The issue is the variable section accepts some data at run time. Say userId, which I already defined in the user defined variables section. Say userId - 100, is defined in that section.
Say suppose the variables is of this type:
{
"users" : {
"userId" : "100",
"date" : "2021-08-23T10:12:13:666666"
}
}
In this case how do I pass userId at run time ?
And I have a bean shell pre-processor in which I have generated the current date time and stored that in a string variable. How do I pass that string variable at run time in this body.

Not knowing your GraphQL contract/query it is quite hard or even impossible to come up with a comprehensive answer.
If you want to parameterize your GraphQL query you need to remember that JMeter Variables syntax conflicts with GraphQL variables syntax, that's why GraphQL HTTP Request has "Variables" section
Given the following example GraphQL server: you can request a droid with ID of 2000 details using the next query:
query {
droid(id: 2000){
id
name
friends{
name
}
appearsIn
primaryFunction
}
}
and it will work:
However if you need to make this id of 2000 dynamic you will need to take some extra steps, like in variables section put the following JSON:
{
"id": "2000"
}
or if you want to parameterize it with User Defined Variables you can use the JMeter Variable reference here:
{
"id": "${id}"
}
and amend your query to look like:
query ($id: ID!){
droid(id: $id){
id
name
friends{
name
}
appearsIn
primaryFunction
}
}
Demo:
More information: Introducing JMeter 5.4: New Features and Abilities

Related

Pass input variable to output

Is it possible to pass an input variable to the output? I tried something like
this:
query GetUrlTitleDetails(
$geo: Country!
$platform: Platform! = WEB
) {
offers(country: $geo, platform: $platform) {
country
standardWebURL
}
}
but I get this result:
{"message": "Cannot query field \"country\" on type \"Offer\"."}
What are you trying to accomplish here? This is not possible (at least just using a GraphQL document).
Your outputs are defined by the GraphQL server. Not the client. Of course the output is derived using the inputs, but you just can't directly set outputs from your request. To do this, you have to change your GraphQL server.
Your code sample just shows your GraphQL document, which is simply the client request. If you want to pass the input variable to the output, you have to write the GraphQL service to pass the input to the output.
If I really want to do this, I'd do something like this (using Ballerina since I am more familiar with it).
import ballerina/graphql;
service on new graphql:Listener(9090) {
resource function get offers(string country, string platform) returns Offer {
return {
country: country,
standardWebURL: "<URL>"
};
}
}
type Offer record {|
string country;
string standardWebURL;
|};
Running this service, you can get the input country as part of the output, from your provided document.

Passing variable in insomnia graphql request

in the graphql request i need to use environment variables, but i didn't find correct way to do this. in my request i have to provide id to get information about certain county.
i've tried to address them as _.var_name and no result. I've tried to call them like $var_name but it says that this variable is not defined. So question is how to address environment variable in query, or how to define $ss variable from my example on the picture ?
Thank you!
Query
query affiliations($last: Int) {
affiliations(last: $last) {
totalCount
}
}
Query variables
{
"last": "{{ _.envvar_name }}"
}

GraphQL - Execute sub query conditionally

I'm trying to optimise the query executed by some of my react components that are shared across the whole app, such as Footer and Header components.
I'm trying not to fetch the Student Solution details when the variable institutionPath is not provided.
query organisationAndInstitution($organisationName: String!, $institutionPath: String!, $fetchInstitution: Boolean!){
organisation(where: {
name: $organisationName
}){
name
}
studentSolutionRelationships(where:{
AND: [
{
status: PUBLISHED
},
{
studentSolution: {
status: PUBLISHED
}
}
]
}) #include(if: $fetchInstitution) {
status
}
}
To do so, I added a fetchInstitution boolean variable and added the #include(if: $fetchInstitution) directive.
But directives seem to apply only on fields, not on whole queries. So I wonder if what I want to do is possible, because the way I wrote it is invalid.
Any field in a GraphQL document can be explicitly included using the #include directive or explicitly excluded using the #skip directive. The directive should be provided after the field name and arguments, but before the field's selection set, if it has one, as shown in your question:
studentSolutionRelationships(where:{
#...input fields omitted for brevity
}) #include(if: $fetchInstitution) {
status
}
The directive takes a single argument (if) which must be a Boolean value. This value may be a literal (i.e. true or false) or a variable of the Boolean type. GraphQL does not provide a way to evaluate expressions -- any conditional logic has to be reside in the client code and be used to determine the value of the variable passed to the if argument.
The directives may be applied to any field in a document, including root-level ones like studentSolutionRelationships and organisation in the question. In fact, you can exclude all root fields using these directives -- just keep in mind that in such a scenario, the query will still run and just return an empty object.
In other words, your approach here is correct. If the query is failing, it's because of an unrelated issue.

Populate an object and pass it in a request parameter in GraphQL

How can we populate an object and pass it in a request parameter in GraphQL. For example, i want to get rid of sequence of parameters here in the GraphQL request and want to create an object and pass it as a single parameter.
{
allBooks(first:20, orderBy:"myRating"){
isn
title
authors
publisher
}
}
You can use GraphQL Input Types.
In your schema definition you need to define the input into something like:
input BooksInput {
first: Int
orderBy: String
}
And require it as the args type in your query, then use it as:
{
allBooks($input: {first:20, orderBy:"myRating"}){
isn
title
authors
publisher
}
}

Is there a way to pass a fragment to graphiql?

It's possible to pass a query, but apparently not a fragment:
server.use('/graphiql', graphiqlExpress({
endpointURL: '/graphql',
query: `# Welcome to GraphiQL
query PostsForAuthor {
author(id: 1) {
firstName
posts {
title
votes
}
}
}`}));
Update 10/12/2017
It is possible to send fragments along with a query using Apollo's client:
http://dev.apollodata.com/core/fragments.html
This is not a solution to the original question, however; I would like to pass fragments to a graphiql server instance at startup.
by startup do you mean from the server? if so I don't believe that's how fragments are used. my understanding is as follows:
on the server you provide Types (like User)
on the client you query those Types using queries and fragments
for instance, if you provide type User on the server, on the client graphQL you can use fragments to query that type:
graphQL (client)
fragment authorData on AuthorType{
firstName
posts {
title
votes
}
}
query PostsForAuthor {
author(id: 1) {
...authorData
}
}
As you noticed (and as detailed here) GraphiQL takes a query argument:
query: an optional GraphQL string to use as the initial displayed query, if undefined is provided, the stored query or defaultQuery will be used.
If putting a fragment in as the value for that argument doesn't work, then I don't believe there is any way to start with a fragment ... but really why would you even want to? A fragment by itself isn't executable, and the whole idea is to start GraphiQL with a (executable) query.
If all you want is to be able to copy/paste in some text that you use frequently in your queries, a bookmarklet might be a better idea.

Resources