I'm building a GraphQL service atop a database that returns information about a matching property. The DB query can be empty, return one or many entries.
The property itself is encapsulated in a corresponding class & type:
class Property(graphene.ObjectType):
PROPERTY_ID = graphene.Int()
PROPERTY_TYPE = graphene.String()
DATE_REPORTED = graphene.String()
NO_OF_OWNERS = graphene.String()
OWNER_FULL_NAME = graphene.String()
….
class PropertyType(graphene.ObjectType):
class Meta:
model = Property
Extraction from the DB happens through a tiny util that builds a list of properties and returns that list.
def get_properties(address, full_name):
query = qg.query_properties(address, full_name)
extract = qm.run_query(query)
prop_list = []
for idx, row in extract.iterrows():
prop_cash = extract.iloc[idx]['CASH_REPORTED']
prop_id = extract.iloc[idx]['PROPERTY_ID']
prop_type = extract.iloc[idx]['PROPERTY_TYPE']
prop_date_rep = extract.iloc[idx]['DATE_REPORTED']
prop_no_owners = extract.iloc[idx]['NO_OF_OWNERS']
prop_owner_full_name = extract.iloc[idx]['OWNER_FULL_NAME']
prop_owner_address = extract.iloc[idx]['OWNER_STREET_1']
prop_owner_city = extract.iloc[idx]['OWNER_CITY']
prop_owner_zip = extract.iloc[idx]['OWNER_ZIP']
prop_list.append(Property(
CASH_REPORTED=prop_cash,
PROPERTY_ID=prop_id,
PROPERTY_TYPE=prop_type,
DATE_REPORTED=prop_date_rep,
NO_OF_OWNERS=prop_no_owners,
OWNER_FULL_NAME=prop_owner_full_name,
OWNER_ADDRESS=prop_owner_address,
OWNER_CITY=prop_owner_city,
OWNER_ZIP=prop_owner_zip
))
return prop_list
That code works well and returns a list of properties. When exposing that function as GraphQL with Graphene, I get some troubles when using the following schema: import graphene class Query(graphene.ObjectType): report = graphene.Field(PropertyReport, address=graphene.String(), full_name=graphene.String()) properties = graphene.List(PropertyType, address=graphene.String(), full_name=graphene.String())
async def resolve_report(self, info, address, full_name):
nr_prop, cash_sum, cash_avg, cash_min, cash_max = await get_report(address, full_name)
return PropertyReport(
nr_properties=nr_prop,
sum_cash_reported=cash_sum,
avg_cash_reported=cash_avg,
min_cash_reported=cash_min,
max_cash_reported=cash_max
)
async def resolve_properties(self, info, address, full_name):
props = await get_properties(address=address, full_name=full_name)
return props
# return Property.objects.all()
schema = graphene.Schema(query=Query)
The property report resolver, which returns a single object, works as expected as GraphQL endpoint and I can query it with any GraphQL client.
The properties resolver, however, doesn't work and throws the following error:
AssertionError: PropertyType fields must be a mapping (dict / OrderedDict)
with field names as keys or a function which returns such a mapping.
If I understand the error correctly, it just says it cannot map the object property fields in each object for whatever reason.
I struggle with understanding how Graphene handles collection of objects. The documentation says, just make it list of objects assuming and so I declared properties as a list of properties but for some reason the resolver does not match it.
Do I need two resolvers, one for the object, and one for the list?
I am not exactly sure what's wrong here but I get a sense that I am overlooking something.
Thank you