Ariadne Codegen 0.8
Ariadne Codegen 0.8 has been released!
This release brings support for file uploads, pydantic v2 compliance, improved custom scalars handling, and few other features and fixes.
File uploads
From now on, the default base client (sync or async) checks if any part of variables is an instance of Upload. If such an instance is found, the client sends a multipart request according to GraphQL multipart request specification. Upload is a class that stores necessary data about the file:
class Upload:
def __init__(self, filename: str, content: IOBase, content_type: str):
self.filename = filename
self.content = content
self.content_type = content_type
It is part of the generated client, and can be imported from it:
from {target_package_name} import Upload
By default, this class represents the graphql scalar Upload, but using custom scalar configuration, it can also be used for other scalars, e.g:
[tool.ariadne-codegen.scalars.OTHERSCALAR]
type = "Upload"
Pydantic v2
Version 0.8 changes the supported version of pydantic to >=2.0.0,<3.0.0. List of changes in the generated client:
- Renamed
parse_objtomodel_validate. - Renamed
dicttomodel_dump. - Preconfigured
BaseModelusesmodel_configattribute instead ofConfigclass. - Renamed
update_forward_refstomodel_rebuild. - Changed json encoder used by default base clients from
pydantic.json.pydantic_encodertopydantic_core.to_jsonable_python. - Optional input fields now have an explicit default
Nonevalue (if the schema doesn't specify another value).
Improved custom scalars
In 0.8, we removed custom scalar logic from the preconfigured BaseModel, instead using pydantic's BeforeValidator and PlainSerializer. Now for every custom scalar provided in pyproject.toml, we generate an annotation that is used in generated arguments, results, and input models.
Example of generated annotations:
[tool.ariadne-codegen]
...
files_to_include = [".../type_b.py"]
[tool.ariadne-codegen.scalars.SCALARA]
type = "str"
[tool.ariadne-codegen.scalars.DATETIME]
type = "datetime.datetime"
[tool.ariadne-codegen.scalars.SCALARB]
type = ".type_b.TypeB"
parse = ".type_b.parse_b"
serialize = ".type_b.serialize_b"
# scalars.py
from datetime import datetime
from typing import Annotated
from pydantic import BeforeValidator, PlainSerializer
from .type_b import TypeB, parse_b, serialize_b
SCALARA = str
DATETIME = datetime
SCALARB = Annotated[TypeB, PlainSerializer(serialize_b), BeforeValidator(parse_b)]
BaseModel no longer depends on scalars.py, so now we can customize file name through the scalars_module_name option.
Scalars file has complellty different structure, so we removed generate_scalars_parse_dict and generate_scalars_serialize_dict plugin hooks. Instead, we introduced generate_scalar_annotation and generate_scalar_imports hooks.
Mixin directive
Ariadne Codegen 0.8 brings support for using the mixin directive on fragment definitions.
For example, given this fragment definition:
fragment fragmentA on TypeA @mixin(from: ".mixins", import: "MixinA") {
fieldA
}
Generated FragmentA will inherit from MixinA:
# fragments.py
from .base_model import BaseModel
from .mixins import MixinA
class FragmentA(BaseModel, MixinA):
field_a: int = Field(alias="fieldA")
Additionally, from now on, the mixin directive will be excluded from the operation string, which is sent to a graphql server.
Field names
Version 0.8 introduces improvements in generating field names. It will append _ to generated field name that would be already reserved by pydantic BaseModel's methods and attributes.
We also added handling of field names which consist only of underscores. It will be generated as underscore_named_field_. This behavior has the lowest priority in our name processing, so such a field's name can be altered by using an alias or utilizing process_name plugin hook.
Unified annotations
We changed the generated client to use typing.Dict and typing.List instead of dict and list. That way, used annotations don't prevent using a generated client with older versions of Python.
Changelog
- Added support for
Uploadscalar. Added support for file uploads toAsyncBaseClientandBaseClient. - Added validation of defined operations against the schema.
- Removed
mixindirective from fragment string included in operation string sent to server. - Added support for
mixindirective on fragments definitions. - Added support for fragments defined on subtype of field's type.
- Added default representation for a field name consisting only of underscores.
- Changed generated client and models to use pydantic v2.
- Changed custom scalars implementation to utilize pydantic's
BeforeValidatorandPlainSerializer. Addedscalars_module_nameoption. Replacedgenerate_scalars_parse_dictandgenerate_scalars_serialize_dictwithgenerate_scalar_annotationandgenerate_scalar_importsplugin hooks. - Unified annotations in generated client to be compatible with python < 3.9.
- Fixed generating default values of input types from remote schemas.
- Changed generating of input and result field names to add
_to names reserved by pydantic.