Skip to main content

License Release Docs Code Coverage Build Status Travis CI Blog

GraphQL-From-Struct

A simple one-method library makes a GraphQL query from Python data structures.

Table of Contents

  1. Installation

  2. Usage

  3. Exceptions

  4. Parameters

  5. Reserved keywords

  6. Examples

Installation

pip install graphql_from_struct

Usage

# 1. Import GqlFromStruct class

from graphql_from_struct import GqlFromStruct

# 2. Make a query

struct = {'hero':{'@fields':['name']}}

# 3. Generate GraphQL

gql = GqlFromStruct.from_struct(struct)

# Or use OOP-style:

foo = GqlFromStruct(struct)

gql = foo.query()

print (gql)

You should see such result:

query{
        hero{
                name
            }
    }

Exceptions

The module raises GqlFromStructException in case of empty or wrong data structure input.

Parameters

GqlFromStruct() constructor and .from_struct() method take 3 arguments: a struct (default None), a minimize (optional, default False) flag and a force_quotes (optional, default 0) setting. Code:

foo = GqlFromStruct({'hero':{'@fields':['name']}}, True)

# or foo = GqlFromStruct(struct = {'hero':{'@fields':['name']}}, minimize = True)

gql = foo.query()

# or

gql = GqlFromStruct.from_struct({'hero':{'@fields':['name']}}, True)

print (gql)

gives you:

query{hero{name}}

By default the GraphQL-From-Struct sets quotes for any string with spaces. You can change it with the force_quotes flag. It enforces quoting parameters and arguments with 1 value, disables any quotes with -1 or enables only arguments quoting with 2:

gql = GqlFromStruct.from_struct({'hero':{'@fields':['name']}}, True, 1)

print (gql)

gives you:

"query"{"hero"{"name"}}

Or

gql = GqlFromStruct.from_struct({'he ro':{'@fields':['name']}}, True, -1)

print (gql)

gives you:

query{he ro{name}}

Or

gql = GqlFromStruct.from_struct('human':{'@fields':['name', 'height'], '@args':{'id':['foo', 'bar']}}, True, 2)

print (gql)

gives you:

query{human(id:["foo", "bar"]){name height}}

Reserved keywords

Words @alias, @args, @fields, @fragments, @fragment_name, @directives, @include, @mutations, @operation_name, @queries, @query, @skip, @variables are reserved and used for query constructing.

Examples

Examples are shown in the same order as in the GraphQL documentation.

Fields

Use @fields keyword:

struct = {'hero':{'@fields':['name']}}

print (GqlFromStruct.from_struct(struct))

Output:

query{
        hero{
                name
            }
    }

You can use arbitrary field nesting:

struct = {'hero':{'@fields':['name', {'friends':{'@fields':['name']}}]}}

print (GqlFromStruct.from_struct(struct))

Output:

query{
        hero{
                name
                friends{
                        name
                    }
            }
    }

Arguments

Use @args keyword:

struct = {'human':{'@fields':['name', 'height'], '@args':{'id':'"1000"'}}}

print (GqlFromStruct.from_struct(struct))

Output:

query{
        human(
            id : "1000"
            ){
                name
                height
            }
    }

or:

struct = {
  'human': {
    '@fields': ['name', {
      'height': {
        '@args': {
          'unit': 'FOOT'
        }
      }
    }],
    '@args': {
      'id': "1000"
    }
  }
}

print (GqlFromStruct.from_struct(struct))

Output:

query{
        human(
            id : 1000
            ){
                name
                height(
                    unit : FOOT
                    )
            }
    }

Note: GraphQL-From-Struct puts double quotes by default only for values with spaces. Like that:

query = {'human':{'@fields':['name', 'height'], '@args':{'id':'1000 meters'}}}

Output:

query{
        human(
            id : "1000 meters"
            ){
                name
                height
            }
    }

Single words or numerical values are output in the form in which you passed them.

query = {'human':{'@fields':['name', 'height'], '@args':{'id':1000}}}
query{
        human(
            id : 1000
            ){
                name
                height
            }
    }
Default arguments

You can set default values of arguments:

struct = {'human':{'@fields':['name', 'height'], '@args':{'$first': {'Int':'3'}}}

print (GqlFromStruct.from_struct(struct))

Output:

query{
        human(
            $first : Int = 3
            ){
                name
                height
            }
    }

Aliases

Use @alias keyword:

struct = [{
  'hero': {
    '@alias': 'empireHero',
    '@args': {
      'episode': "EMPIRE"
    },
    '@fields': ['name']
  }
}, {
  'hero': {
    '@alias': 'jediHero',
    '@args': {
      'episode': "JEDI"
    },
    '@fields': ['name']
  }
}]

print (GqlFromStruct.from_struct(struct))

Output:

query{
        empireHero : hero(
            episode : EMPIRE
            ){
                name
            }
        jediHero : hero(
            episode : JEDI
            ){
                name
            }
    }

Fragments

Use @fragments and @fragment_name keywords for fragments setting up. Use @query and @queries for join some queries into one.

struct = {
            "@queries": [{
              '@query': [{
                  'hero': {
                    '@alias': 'leftComparison',
                    '@args': {
                      'episode': "EMPIRE"
                    },
                    '@fields': ['...comparisonFields']
                  }
                },
                {
                  'hero': {
                    '@alias': 'rightComparison',
                    '@args': {
                      'episode': "JEDI"
                    },
                    '@fields': ['...comparisonFields']
                  }
                }
              ]
            }],
            "@fragments": [{
              'Character': {
                '@fragment_name': 'comparisonFields',
                '@fields': ['name', 'appearsIn', {
                  'friends': {
                    '@fields': ['name']
                  }
                }]
              }
            }]
          }

print (GqlFromStruct.from_struct(struct))

Output:

query{
        leftComparison : hero(
            episode : EMPIRE
            ){
                ...comparisonFields
            }
        rightComparison : hero(
            episode : JEDI
            ){
                ...comparisonFields
            }
    }
fragment comparisonFields on Character{
        name
        appearsIn
        friends{
                name
            }
    }
Using variables inside fragments
struct = {
  "@queries": [{
    '@args': {
      '$first': {
        'Int': '3'
      }
    },
    '@operation_name': 'HeroComparison',
    '@query': [{
        'hero': {
          '@alias': 'leftComparison',
          '@args': {
            'episode': "EMPIRE"
          },
          '@fields': ['...comparisonFields']
        }
      },
      {
        'hero': {
          '@alias': 'rightComparison',
          '@args': {
            'episode': "JEDI"
          },
          '@fields': ['...comparisonFields']
        }
      }
    ]
  }],
  "@fragments": [{
    'Character': {
      '@fragment_name': 'comparisonFields',
      '@fields': ['name', {
        'friendsConnection': {
          '@args': {
            'first': '$first'
          },
          '@fields': ['totalCount', {
            'edges': {
              '@fields': [{
                'node': {
                  '@fields': ['name']
                }
              }]
            }
          }]
        }
      }]
    }
  }]
}

print (GqlFromStruct.from_struct(struct))

Output:

query HeroComparison (
$first : Int = 3
){
        leftComparison : hero(
            episode : EMPIRE
            ){
                ...comparisonFields
            }
        rightComparison : hero(
            episode : JEDI
            ){
                ...comparisonFields
            }
    }
fragment comparisonFields on Character{
        name
        friendsConnection(
            first : $first
            ){
                totalCount
                edges{
                        node{
                                name
                            }
                    }
            }
    }

Operation name

Use @operation_name keyword:

struct =  {
   '@queries': [{
     '@operation_name': 'HeroNameAndFriends',
     '@query': {
       'hero': {
         '@fields': ['name', {
           'friends': {
             '@fields': ['name']
           }
         }]
       }
     }
   }]
 }

print (GqlFromStruct.from_struct(struct))

Output:

query HeroNameAndFriends{
        hero{
                name
                friends{
                        name
                    }
            }
    }

Variables

Use @variables block at the same high level nesting as @queries:

struct = {
            '@queries': [{
              '@operation_name': 'HeroNameAndFriends',
              '@query': {
                'hero': {
                  '@fields': ['name', {
                    'friends': {
                      '@fields': ['name']
                    }
                  }]
                }
              }
            }],
            '@variables': {
              "episode": "JEDI"
            }
          }

print (GqlFromStruct.from_struct(struct))

Output:

query HeroNameAndFriends{
        hero{
                name
                friends{
                        name
                    }
            }
    }
{
    "episode": "JEDI"
}
Default variables

Use @fields keyword:

struct =  {
            '@queries': [{
              '@operation_name': 'HeroNameAndFriends',
              '@args': {
                '$episode': {
                  'Episode': 'JEDI'
                }
              },
              '@query': {
                'hero': {
                  '@fields': ['name', {
                    'friends': {
                      '@fields': ['name']
                    }
                  }]
                }
              }
            }],
            '@variables': {
              "episode": "JEDI"
            }
          }

print (GqlFromStruct.from_struct(struct))

Output:

query HeroNameAndFriends (
$episode : Episode = JEDI
){
        hero{
                name
                friends{
                        name
                    }
            }
    }
{
    "episode": "JEDI"
}

Directives

Use @directives keyword and @skip or @include as directives:

struct = {
  '@queries': [{
    '@operation_name': 'Hero',
    '@args': {
      '$episode': 'Episode',
      '$withFriends': 'Boolean!'
    },
    '@query': {
      'hero': {
        '@args': {
          'episode': '$episode'
        },
        '@fields': ['name', {
          'friends': {
            '@fields': ['name'],
            '@directives': {
              '@include': '$withFriends'
            }
          }
        }]
      }
    }
  }],
  '@variables': {
    "episode": "JEDI"
  }
}

print (GqlFromStruct.from_struct(struct))

Output:

query Hero (
$episode : Episode,
$withFriends : Boolean!
){
        hero(
            episode : $episode
            ){
                name
                friends @include (if :  $withFriends){
                        name
                    }
            }
    }
{
    "episode": "JEDI"
}

Mutations

Use @mutations keyword:

struct = {
  '@mutations': [{
    '@operation_name': 'CreateReviewForEpisode',
    '@args': {
      '$episode': 'Episode!',
      '$review': 'ReviewInput!'
    },
    '@query': {
      'createReview': {
        '@args': {
          'episode': '$ep',
          'review': '$review'
        },
        '@fields': ['stars', 'commentary']
      }
    }
  }],
  '@variables': {
    "episode": "JEDI",
    "review": {
      "stars": 5,
      "commentary": "This is a great movie!"
    }
  }
}

print (GqlFromStruct.from_struct(struct))

Output:

mutation CreateReviewForEpisode (
$episode : Episode!,
$review : ReviewInput!
){
        createReview(
            episode : $ep,
            review : $review
            ){
                stars
                commentary
            }
    }
{
    "episode": "JEDI",
    "review": {
        "stars": 5,
        "commentary": "This is a great movie!"
    }
}

Inline Fragments

Nothing special needed.

struct =  {
   "@queries": [{
     '@args': {
       '$ep': 'Episode!'
     },
     '@operation_name': 'HeroForEpisode',
     '@query': [{
       'hero': {
         '@args': {
           'episode': '$ep'
         },
         '@fields': ['name',
           {
             '... on Droid': {
               '@fields': ['primaryFunction']
             }
           },
           {
             '... on Human': {
               '@fields': ['height']
             }
           }
         ]
       }
     }]
   }]
 }

print (GqlFromStruct.from_struct(struct))

Output:

query HeroForEpisode (
$ep : Episode!
){
        hero(
            episode : $ep
            ){
                name
                ... on Droid{
                        primaryFunction
                    }
                ... on Human{
                        height
                    }
            }
    }

Meta fields

Use meta field as usual field:

struct = {
  'search': {
    '@args': {
      'text': 'an'
    },
    '@fields': ['__typename',
      {
        '... on Human': {
          '@fields': ['name']
        }
      },
      {
        '... on Droid': {
          '@fields': ['name']
        }
      },
      {
        '... on Starship': {
          '@fields': ['name']
        }
      }
    ]
  }
}

print (GqlFromStruct.from_struct(struct))

Output:

query{
        search(
            text : an
            ){
                __typename
                ... on Human{
                        name
                    }
                ... on Droid{
                        name
                    }
                ... on Starship{
                        name
                    }
            }
    }

Metadata

Release files for graphql-from-struct 1.0.3

For a detailed explanation of source distributions (sdists) and built distributions (wheels), please see the package formats documentation.

Source distribution (sdist)

Source distribution for graphql-from-struct 1.0.3
File Size Uploaded
graphql-from-struct-1.0.3.tar.gz 12.6 kB Details

Built distribution (wheel)

Table of built distributions (wheels) for graphql-from-struct 1.0.3
File Interpreter ABI Platform
graphql_from_struct-1.0.3-py2.py3-none-any.whl Python 2, Python 3 none any Details

Total release size: 20.2 kB

Release files / graphql-from-struct-1.0.3.tar.gz

Download URL graphql-from-struct-1.0.3.tar.gz
Size 12.6 kB
Tags Source
SHA-256 checksum
How to use checksums
adeea2a1c014b39e719668689f37eca6656e4d61590fe2305f8c2b9fd63b0a48
BLAKE2b-256 checksum
How to use checksums
632f82d1513eb1a4445d3460e2e37ae441fffbe7159462a540756f4f5fa67449
Upload date
Uploaded using Trusted Publishing?
What is trusted publishing?
No
Uploaded via twine/3.3.0 pkginfo/1.7.0 requests/2.25.1 setuptools/49.2.1 requests-toolbelt/0.9.1 tqdm/4.56.2 CPython/3.9.1

Release files / graphql_from_struct-1.0.3-py2.py3-none-any.whl

Download URL graphql_from_struct-1.0.3-py2.py3-none-any.whl
Size 7.5 kB
Tags Python 2 Python 3
SHA-256 checksum
How to use checksums
34e6519ffef8009ce629f5a0f73df7ce544640786a40295855b58ef5d4cca2df
BLAKE2b-256 checksum
How to use checksums
c3128cb43237d45ed9336076b3195a70a7a15a13a8a7c282954b49b37f876e8d
Upload date
Uploaded using Trusted Publishing?
What is trusted publishing?
No
Uploaded via twine/3.3.0 pkginfo/1.7.0 requests/2.25.1 setuptools/49.2.1 requests-toolbelt/0.9.1 tqdm/4.56.2 CPython/3.9.1

Release history Release notifications | RSS feed

This release

1.0.3 This release

2 release files

1.0.2

2 release files

1.0.1

2 release files

1.0.0

2 release files

Anthropic, PBC Visionary sponsor Bloomberg Visionary sponsor Hudson River Trading Visionary sponsor Meta Visionary sponsor NVIDIA Visionary sponsor Microsoft Sustainability sponsor Depot Continuous Integration AWS Cloud computing and Security Sponsor Datadog Monitoring Fastly CDN Google Download Analytics Sentry Error logging StatusPage Status page