Skip to main content

qenerate

qenerate is a pluggable code generator for GraphQL Query and Fragment Data Classes. It works hand in hand with GraphQL clients like gql. Clients like gql return nested untyped dictionaries as result to a query. qenerate generated classes easily transform these nested untyped dictionaries into concrete classes. qenerate itself is not a GraphQL client and solely focuses on generating code for transforming untyped dictionaries into concrete types.

Installation

Releases are published on pypi.

pip install qenerate

Usage

Introspection

In a first step we must obtain the GQL schema in the form of an introspection query:

qenerate introspection http://my-gql-instance:4000/graphql > introspection.json

The introspection.json is used in a next step to map concrete types to your queries and fragments.

Code Generation

qenerate code -i introspection.json dir/to/gql/files

An introspection.json and a (nested) directory holding all your *.gql files are given. qenerate then generates data classes for every *.gql file it encounters while traversing the given directory.

qenerate expects that a .gql file contains exactly one query, mutation or fragment definition.

Note, that the given directory and every gql. file in it share the same scope. I.e., within this scope fragment and query names must be unique. Further, you can freely use any fragment within queries, as long as the fragment is defined somewhere within the scope (directory).

Example for Single Query

Single query and its generated classes.

Example for Query using a Fragment

We define a re-usable fragment which results in the following generated re-usable data classes.

The fragment is used in a query and imported in the generated python file.

More Examples

qenerate is actively used in our qontract-reconcile project. There you can find a lot of examples on how generated classes look like in more detail.

Plugins

qenerate follows a plugin based approach. I.e., multiple code generators are supported. Choosing a code generator is done inside the query file, e.g., the following example will generate data classes using the pydantic_v2 plugin:

# qenerate: plugin=pydantic_v2
query {
    ...
}

By choosing a plugin based approach, qenerate can extent its feature set creating new plugins while at the same time keeping existing plugins stable and fully backwards compatible.

Currently available plugins are:

Feature Flags

qenerate leverages feature flags to configure the behavior of the generator. Feature flags are passed to the generator via comments in your .gql definition file.

Plugin

# qenerate: plugin=<plugin-id>

This feature flag tells qenerate which plugin it should use to generate the code for the given definition.

Custom Type Mapping

You can tell qenerate to map a primitive GQL type (a.k.a. Scalar) to something that you want. This can be handy if your codebase expects other primitive datatypes like, e.g., str instead of Json or datetime. This can be especially useful for custom GQL primitives.

# qenerate: map_gql_scalar=JSON -> str

The above will tell qenerate to map the GQL JSON type to str instead of pydantic's Json. You can also map multiple types, e.g.,

# qenerate: map_gql_scalar=JSON -> str
# qenerate: map_gql_scalar=DateTime -> str

Naming Collision Strategy

# qenerate: naming_collision_strategy=[PARENT_CONTEXT | ENUMERATE]

This feature flag tells qenerate how to deal with naming collisions in classes. In GraphQL it is easy to query the same object in a nested fashion, which results in re-definitions of the type. We call this naming collision. A naming collision strategy defines how to adjust recurring names to make them unique.

PARENT_CONTEXT

This is the default strategy if nothing else is specified. It uses the name of the parent node in the query as a prefix.

ENUMERATE

This strategy adds the number of occurrences of this name as a suffix.

However, in most cases it might be cleaner to define a re-usable fragment instead of relying on a collision strategy. Here are some fragment examples.

Limitations

Overlapping properties

As of now qenerate does not support operations with overlapping properties. E.g.,

fragment MyFragment on Namespace {
    b {
        e
        f
    }
}

query MyQuery {
    namespaces {
        a
        ... MyFragment
        b {
            c  # This overlapps with properties in MyFragment
        }
    }
}

The above is valid GQL syntax and will merge properties defined in MyFragment and b { c } into b {c,e,f}. However, currently qenerate will fail to deduce proper base classes for these overlapps. Work on this is being conducted in #77.

Development

CI

CI/CD is done via Konflux

Build and Dependency Management

qenerate uses UV as build and dependency management system.

Formatting

qenerate uses ruff for code checking and formatting.

Release

  • Bump the version in pyproject.toml
  • Update CHANGELOG.md
  • Update the uv.lock file via uv sync -U
  • Create and merge a PR

Architecture

The architecture is described in more detail in this document.

Release files for qenerate 0.10.0

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

Source distribution (sdist)

Source distribution for qenerate 0.10.0
File Size Uploaded
qenerate-0.10.0.tar.gz 18.0 kB Details

Built distribution (wheel)

Table of built distributions (wheels) for qenerate 0.10.0
File Interpreter ABI Platform
qenerate-0.10.0-py3-none-any.whl Python 3 none any Details

Total release size: 40.1 kB

Release files / qenerate-0.10.0.tar.gz

Download URL qenerate-0.10.0.tar.gz
Size 18.0 kB
Tags Source
SHA-256 checksum
How to use checksums
d0c8705f3cc703cfd83073d7aa0d67a3966b31458a4133939cf04dbc185155b2
BLAKE2b-256 checksum
How to use checksums
9be08643598848d866d511e2cd836e9999911522fede8ea3209f6ba6800a71ff
Upload date
Uploaded using Trusted Publishing?
What is trusted publishing?
No
Uploaded via uv/0.11.19 {"installer":{"name":"uv","version":"0.11.19","subcommand":["publish"]},"python":null,"implementation":{"name":null,"version":null},"distro":{"name":"Red Hat Enterprise Linux","version":"9.8","id":null,"libc":null},"system":{"name":null,"release":null},"cpu":null,"openssl_version":null,"setuptools_version":null,"rustc_version":null,"ci":null}

Release files / qenerate-0.10.0-py3-none-any.whl

Download URL qenerate-0.10.0-py3-none-any.whl
Size 22.1 kB
Tags Python 3
SHA-256 checksum
How to use checksums
866cbfb0a79a42f12faa17c11cdb40423700be4fbd5d13be640f507e1903e47a
BLAKE2b-256 checksum
How to use checksums
7b9088af4ab390fae8c2c3ab710159b8d531e09275c8e22f37be331d5d7f6f8a
Upload date
Uploaded using Trusted Publishing?
What is trusted publishing?
No
Uploaded via uv/0.11.19 {"installer":{"name":"uv","version":"0.11.19","subcommand":["publish"]},"python":null,"implementation":{"name":null,"version":null},"distro":{"name":"Red Hat Enterprise Linux","version":"9.8","id":null,"libc":null},"system":{"name":null,"release":null},"cpu":null,"openssl_version":null,"setuptools_version":null,"rustc_version":null,"ci":null}

Release history Release notifications | RSS feed

This release

0.10.0 This release

2 release files

0.9.2

2 release files

0.9.1

2 release files

0.9.0

2 release files

0.8.1

2 release files

0.8.0

2 release files

0.7.0

2 release files

0.6.5

2 release files

0.6.4

1 release file

0.6.3

1 release file

0.6.2

1 release file

0.6.1

1 release file

0.6.0

1 release file

0.5.2

1 release file

0.5.1

1 release file

0.5.0

1 release file

0.4.7

1 release file

0.4.6

1 release file

0.4.5

1 release file

0.4.4

1 release file

0.4.3

1 release file

0.4.2

1 release file

0.4.1

1 release file

0.4.0

1 release file

0.3.0

1 release file

0.2.8

1 release file

0.2.7

1 release file

0.2.6

1 release file

0.2.5

1 release file

0.2.4

1 release file

0.2.3

1 release file

0.2.2

1 release file

0.2.1

1 release file

0.2.0

1 release file

0.1.5

1 release file

0.1.4

1 release file

0.1.3

1 release file

0.1.2

1 release file

0.1.1

1 release file

0.1.0

1 release file

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