【问题标题】:HotChocolate GraphQL filtering on GUID基于 GUID 的 HotChocolate GraphQL 过滤
【发布时间】:2021-11-25 19:59:38
【问题描述】:

我对 GraphQL 的了解非常有限,因为我仍在学习过程中。现在我偶然发现了一个问题,如果没有一些帮助,我无法自己解决。

我在服务中使用 HotChocolate。

我有一个 ConsumerProductCategory 类,GuidId,它的父类也是 ConsumerProductCategory(想想类别 > 子类别 > ...)

现在我想获取特定类别的子类别,在 linq 中你会写:

.Where(cat => cat.Parent.Id == id)

首先让我们从我们的类开始:

public class BaseViewModel : INode
{
    public virtual Guid Id { get; set; }
}


public class ConsumerProductCategory : BaseViewModel
{
    public ConsumerProductCategory()
    {
    }

    public string Name { get; set; }

    [UsePaging]
    [UseFiltering]
    [UseSorting]
    public List<ConsumerProduct> Products { get; set; } = new List<ConsumerProduct>();

    public ConsumerProductCategoryImage Image { get; set; }

    public ConsumerProductCategory Parent { get; set; } = null;

    public bool HasParent => this.Parent != null;
}

对象类型定义如下:

public class ConsumerProductCategoryType : ObjectType<ConsumerProductCategory>
{
    protected override void Configure(IObjectTypeDescriptor<ConsumerProductCategory> descriptor)
    {
        descriptor
            .Name(nameof(ConsumerProductCategory));

        descriptor
            .Description("Categories.");

        descriptor
            .Field(x => x.Id)
            //.Type<UuidType>()
            .Type<IdType>()
            .Description($"{nameof(ConsumerProductCategory)} Id.");

        descriptor
            .Field(x => x.Name)
            .Type<StringType>()
            .Description($"{nameof(ConsumerProductCategory)} name.");

        descriptor
            .Field(x => x.Parent)
            .Description($"{nameof(ConsumerProductCategory)} parent category.");

        descriptor
            .Field(x => x.Products)
            .Description($"{nameof(ConsumerProductCategory)} products.");

        descriptor
           .ImplementsNode()
           .IdField(t => t.Id)
           .ResolveNode((context, id) => context.Service<IConsumerProductCategoryService>().GetByIdAsync(id));
    }
}

获取“主要”类别的查询如下:

query GetAllCategories {
  consumerProductCategories(
    #request: { searchTerm: "2"}
    first: 10
    after: null
    where: { hasParent: { eq: false } }
    order: {
      name: ASC
    }
  ) {
    nodes {
      id
      name
      image {
        url
        alt
      }
    }
    pageInfo {
      endCursor
      hasNextPage
    }
  }
}

这会返回这个结果:

{
  "data": {
    "consumerProductCategories": {
      "nodes": [
        {
          "id": "Q29uc3VtZXJQcm9kdWN0Q2F0ZWdvcnkKZ2EyOTYxNmRlMWMzMjQ4ZTU4YTU2YzRjYjdhMGQ5NmY5",
          "name": "Category 1",
          "image": {
            "url": "https://picsum.photos/200",
            "alt": "Category 1 Image"
          }
        },
        {
          "id": "Q29uc3VtZXJQcm9kdWN0Q2F0ZWdvcnkKZ2NmZWI0YzNiMGQyNjQyOWI4MGU0MmQ1NGNjYWE1N2Q4",
          "name": "Category 2",
          "image": {
            "url": "https://picsum.photos/200",
            "alt": "Category 2 Image"
          }
        },
        {
          "id": "Q29uc3VtZXJQcm9kdWN0Q2F0ZWdvcnkKZ2I0MjhjYWE2NGMxNTQ4MTdiMjM1ZWFhZWU3OGRhYWYz",
          "name": "Category 3",
          "image": {
            "url": "https://picsum.photos/200",
            "alt": "Category 3 Image"
          }
        }
      ],
      "pageInfo": {
        "endCursor": "Mg==",
        "hasNextPage": false
      }
    }
  }
}

我注意到的第一件事是 Id (Guid) 被更改为一些 base64 编码的字符串。

很奇怪,但如果我这样做:

query {
      node(
        id: "Q29uc3VtZXJQcm9kdWN0Q2F0ZWdvcnkKZ2EyOTYxNmRlMWMzMjQ4ZTU4YTU2YzRjYjdhMGQ5NmY5"
      ) {
        ... on ConsumerProductCategory {
          id
          name
        }
        
      }
    }

这完全有效,结果:

{
  "data": {
    "node": {
      "id": "Q29uc3VtZXJQcm9kdWN0Q2F0ZWdvcnkKZ2EyOTYxNmRlMWMzMjQ4ZTU4YTU2YzRjYjdhMGQ5NmY5",
      "name": "Category 1"
    }
  }
}

但是,现在我想过滤 Parent.Id,

query GetSubcategories {
  consumerProductCategories(    
    first: 10
    after: null
    where: { parent: { id: { eq: "Q29uc3VtZXJQcm9kdWN0Q2F0ZWdvcnkKZ2NmZWI0YzNiMGQyNjQyOWI4MGU0MmQ1NGNjYWE1N2Q4"}} }
    order: {
      name: ASC
    }
  ) {
    nodes {
      id
      name
      image {
        url
        alt
      }
      parent {
        id
      }
    }
    pageInfo {
      endCursor
      hasNextPage
    }
  }
}

这给出了一个错误,即我执行“eq”的字段类型不正确,这是有道理的,因为在数据中它实际上是一个 Guid。

结果:

{
  "errors": [
    {
      "message": "The specified value type of field `eq` does not match the field type.",
      "locations": [
        {
          "line": 5,
          "column": 31
        }
      ],
      "path": [
        "consumerProductCategories"
      ],
      "extensions": {
        "fieldName": "eq",
        "fieldType": "UUID",
        "locationType": "UUID",
        "specifiedBy": "http://spec.graphql.org/June2018/#sec-Values-of-Correct-Type"
      }
    }
  ]
}

我明白为什么它会给我这个错误,但我不知道如何解决这个问题。

我在 Google 上到处找,但没有找到类似的问题,在 HotChocolate 的官方文档中,我真的找不到这个问题的解决方案。

谁能指出我正确的方向?

顺便说一句,将这些“自动生成”的 base64 字符串用作 Id 是一种好习惯,还是有某种方法可以指定不应该发生这种生成并实际返回 Guid?

提前致谢!

【问题讨论】:

    标签: graphql hotchocolate


    【解决方案1】:

    好的,我可以回答我自己的问题,基本上还不支持:github

    我现在所做的只是在基类中添加第二个 Guid:

    这会导致:

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 1970-01-01
      • 2016-11-18
      • 2022-06-24
      • 2020-07-28
      • 2021-09-05
      • 2022-11-11
      • 2021-02-15
      • 2020-06-16
      相关资源
      最近更新 更多