1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 111 112 113 114 115 116 117 118 119 120 121 122 123 124 125 126 127 128 129 130 131 132 133 134 135 136 137 138 139 140 141 142 143 144 145 146 147 148 149 150 151 152 153 154 155 156 157 158 159 160 161 162 163 164 165 166 167 168 169 170 171 172 173 174 175 176 177 178 179 180 181 182 183 184 185 186 187 188 189 190
|
# v1.0 Upgrade Guide
Big changes from v0.10.x to 1.0. While on the surface a lot of this just looks like shuffling around API, the entire codebase has been rewritten to handle some really great use cases and improved performance.
## Backwards Compatibility and Deprecation Warnings
This has been a community project from the start, we need your help making the upgrade as smooth as possible for everybody!
We have done our best to provide backwards compatibility with deprecated APIs.
## Deprecations
- `with_context` is no longer needed. Resolvers now always take the context argument.
Before:
```python
def resolve_xxx(root, args, info):
# ...
```
With 1.0:
```python
def resolve_xxx(root, args, context, info):
# ...
```
- `ObjectType` and `Interface` no longer accept the `abstract` option in the `Meta`.
Inheriting fields should be now achieved using `AbstractType` inheritance.
Before:
```python
class MyBaseQuery(graphene.ObjectType):
my_field = String()
class Meta:
abstract = True
class Query(MyBaseQuery):
pass
```
With 1.0:
```python
class MyBaseQuery(graphene.AbstractType):
my_field = String()
class Query(MyBaseQuery, graphene.ObjectType):
pass
```
- The `type_name` option in the Meta in types is now `name`
- Type references no longer work with strings, but with functions.
Before:
```python
class Query(graphene.ObjectType):
user = graphene.Field('User')
users = graphene.List('User')
```
With 1.0:
```python
class Query(graphene.ObjectType):
user = graphene.Field(lambda: User)
users = graphene.List(lambda: User)
```
## Schema
Schemas in graphene `1.0` are `Immutable`, that means that once you create a `graphene.Schema` any
change in their attributes will not have any effect.
The `name` argument is removed from the Schema.
The arguments `executor` and `middlewares` are also removed from the `Schema` definition.
You can still use them, but by calling explicitly in the `execute` method in `graphql`.
```python
# Old way
schema = graphene.Schema(name='My Schema')
schema.query = Query
schema.mutation = Mutation
# New way
schema = graphene.Schema(
query=Query,
mutation=Mutation
)
```
## Interfaces
For implementing an Interface in an ObjectType, you have to add it onto `Meta.interfaces`.
Like:
```python
from graphene import Interface, ObjectType, String
class Character(Interface):
name = String()
class Human(Character): # Old way, Human will still be an Interface
pass
class Droid(ObjectType): # New way, you have to specify the ObjectType
class Meta:
interfaces = (Character, )
```
## Mutations
Mutation fields have changed the way of usage, before if you have the mutation `MyMutation` you
only have to reference with `graphene.Field(MyMutation)` now it's simply `MyMutation.Field()`
Example:
```python
from graphene import ObjectType, Mutation, String
class ReverseString(Mutation):
class Input:
input = String(required=True)
reversed = String()
def mutate(root, args, context, info):
reversed = args.get('input')[::-1]
return ReverseString(reversed=reversed)
class Query(ObjectType):
reverse_string = graphene.Field(ReverseString) # Old way, will not include the mutation arguments by default
reverse_string = ReverseString.Field()
```
## Nodes
Apart from implementing as shown in the previous section, to use the node field you have to
specify the node Type.
Example:
```python
from graphene import ObjectType, relay
class Query(ObjectType):
node = relay.NodeField() # Old way, NodeField no longer exists. Use Node.Field
node = relay.Node.Field() # New way
```
Also, if you wanted to create an `ObjectType` that implements `Node`, you have to do it
explicitly.
## Django
The Django integration with Graphene now has an independent package: `graphene-django`.
For installing, you have to replace the old `graphene[django]` with `graphene-django`.
- As the package is now independent, you now have to import from `graphene_django`.
- **DjangoNode no longer exists**, please use `relay.Node` instead:
```python
from graphene.relay import Node
from graphene_django import DjangoObjectType
class Droid(DjangoObjectType):
class Meta:
interfaces = (Node, )
```
## SQLAlchemy
The SQLAlchemy integration with Graphene now has an independent package: `graphene-sqlalchemy`.
For installing, you have to replace the old `graphene[sqlalchemy]` with `graphene-sqlalchemy`.
- As the package is now independent, you have to import now from `graphene_sqlalchemy`.
- **SQLAlchemyNode no longer exists**, please use `relay.Node` instead:
```python
from graphene.relay import Node
from graphene_sqlalchemy import SQLAlchemyObjectType
class Droid(SQLAlchemyObjectType):
class Meta:
interfaces = (Node, )
```
|