Это правильный шаблон GraphQL для мутации

У меня есть несколько вопросов о моих шаблонах для API, который я пишу. Написано на бэкэнде в Starlette с использованием MongoDB и GraphQL/Graphene для моих нужд базы данных /api.

Из-за ограниченного объема документации мне иногда трудно определить правильные шаблоны. Одна вещь, которая заставляет меня задуматься, иду ли я в правильном направлении, - это то, как работают мутации. Я знаю, что после запроса результат анализируется резолверами exdef resolve__id(parent, info): return parent['_id'] где родитель - результат, возвращенный из базы данных ex return loads(dumps(val)). Мне кажется, что GraphQL делает то же самое с результатом мутации:return CreateUser(user=user).

Мои вопросы возникают, потому что объект, возвращаемый result = await resources.database.users.insert_one(newUser) содержит только идентификатор createdUser, что означает, что он не может быть возвращен как метод resolve_password():например, для объекта потребуется поле пароля. Из-за этого после каждого запроса вставки я запускаю другой запросuser = await resources.database.users.find_one({"_id": result.inserted_id})чтобы получить только что созданный предмет. Это, в свою очередь, позволяет мне вернуть созданного пользователя в объекте CreateUser, как ожидает GraphQL, согласно документации Graphene: https://docs.graphene-python.org/en/latest/types/mutations/.

По сути, мой вопрос сводится к следующему: шаблон выполнения двух запросов по мутации, ожидаемой для моего инструментария, или я неправильно использую либо функции разрешения, либо какую-либо другую часть GraphQL?

Пожалуйста, дайте мне знать, требуется ли какая-либо другая часть моего кода или дополнительные пояснения. Я включил свой класс User ниже, который содержит весь код, на который я ссылаюсь, для предоставления контекста.

class User(graphene.ObjectType):
    name = graphene.String()
    _id = graphene.String()
    password = graphene.String()
    icon = graphene.String()

    def resolve_name(parent, info):
        return parent['user_name']

    def resolve__id(parent, info):
        return parent['_id']

    def resolve_password(parent, info):
        return parent['password']

    def resolve_icon(parent, info):
        return parent['icon']

class UserInput(graphene.InputObjectType):
    userName = graphene.String(required=True)
    password = graphene.String(required=True)
    icon = graphene.String(required=True)

class CreateUser(graphene.Mutation):
    user = graphene.Field(User)

    class Arguments:
        user_data = UserInput(required=True)


    async def mutate(root, info, user_data=None):
        newUser = {
            'user_name': user_data.userName,
            'password': user_data.password,
            'icon': user_data.icon
        }

        result = await resources.database.users.insert_one(newUser)

        user = await resources.database.users.find_one({"_id": result.inserted_id})
        return CreateUser(user=user)



class UserQuery(graphene.ObjectType):
    user = graphene.Field(User, userName=graphene.String())
    users = graphene.List(User, length=graphene.Int())

    async def resolve_user_by_id(parent, info, userId):
        val = await resources.database.users.find_one({"_id": userId})
        return loads(dumps(val))

    async def resolve_user_by_name(parent, info, userName):
        val = await resources.database.users.find_one({'user_name': userName})
        return loads(dumps(val))
    
    async def resolve_users(parent, info, length):
        val = await resources.database.users.find().to_list(length=length)
        return loads(dumps(val))

class UserMutation(graphene.ObjectType):
    create_user = CreateUser.Field()

0 ответов

Другие вопросы по тегам