【问题标题】:Schema input type always "LinkedHashMap cannot be cast..."架构输入类型始终“无法强制转换 LinkedHashMap...”
【发布时间】:2021-10-24 07:15:48
【问题描述】:

我的 schema.grapqls 看起来像...

scalar BigDecimal
...
input TemplateLineItemInput {
    partMasterId: String!
    partMasterIdPath: String!
    actionType: String!
    actionQuantity: BigDecimal!
}
...
type Mutation {
    ...
    createLineItem(id: ID! input: TemplateLineItemInput!): TemplateBom
}

我的 POJO 都是 Lombok-ie,在我尝试创建 input 之前一直运行良好。

import lombok.Builder;
import lombok.Data;

import java.math.BigDecimal;

@Data
@Builder
public class TemplateLineItemInput {
  private final String partMasterId;
  private final String partMasterIdPath;
  private final String actionType;
  private final BigDecimal actionQuantity;
}

我相信我有正确连接的突变...

@Component
public class TemplateBomDataWiring  implements RuntimeWiringBuilderCustomizer {
  private static final Logger LOG = LoggerFactory.getLogger(TemplateBomDataWiring.class);

  private final TemplateBomService templateBomService;

  public TemplateBomDataWiring(TemplateBomService templateBomService) {
    this.templateBomService = templateBomService;
  }

  @Override
  public void customize(RuntimeWiring.Builder builder) {
    builder.scalar(Scalars.GraphQLBigDecimal);
    builder.scalar(GraphQLDate);
    builder.type("Query", typeWiring -> typeWiring.dataFetcher("templateBom", env -> {
      final String id = env.getArgument("id");
      return templateBomService.getTemplateBom(id);
    }));
    builder.type("Mutation", typeWiring -> typeWiring.dataFetcher("create", env -> {
      final String partMasterId = env.getArgument("partMasterId");
      return templateBomService.createTemplateBom(partMasterId);
    }));
    builder.type("Mutation", typeWiring -> typeWiring.dataFetcher("createLineItem", env -> {
      final String id = env.getArgument("id");
      final TemplateLineItemInput input = env.getArgument("input");
      return templateBomService.createTemplateLineItem(id, input);
    }));
  }

但我无法在 GraphiQL 中解析查询。我没有堆栈跟踪服务器端,我只是在 GraphiQL UI 中得到这个......

{
  "errors": [
    {
      "message": "class java.util.LinkedHashMap cannot be cast to class com.example.boa.domain.TemplateLineItemInput (java.util.LinkedHashMap is in module java.base of loader 'bootstrap'; com.example.boa.domain.TemplateLineItemInput is in unnamed module of loader org.springframework.boot.devtools.restart.classloader.RestartClassLoader @617a9621)",
      "locations": [
        {
          "line": 42,
          "column": 3
        }
      ],
      "path": [
        "createLineItem"
      ],
      "extensions": {
        "classification": "INTERNAL_ERROR"
      }
    }
  ],
  "data": {
    "createLineItem": null
  }
}

我在 https://www.graphql-java.com/documentation/v16/ 文档之外工作

如何让我的 input 类型映射到 graphql-java:16.2 上的 TemplateLineItemInput POJO?

【问题讨论】:

    标签: java spring-boot graphql-java


    【解决方案1】:

    您可以使用 spring boot 来自动定义您的运行时接线。 您可以通过实现来编写查询获取器或变异获取器

    GraphQLQueryResolver
    GraphQLMutationResolver
    

    如果您正在执行运行时接线,除了基本类型之外的复杂输入参数将始终作为键值对传递给 LinkedHashmap。 因此,您必须将传递的linkedHashmap 转换为您期望的类,如下所示。

    ObjectMapper objectMapper = new ObjectMapper();
                String input = objectMapper.writeValueAsString(env.getArgument("input"));
                final String arg = env.getArgument("input");
                return templateBomService.createTemplateLineItem(id, objectMapper.readValue(arg,TemplateLineItemInput.class));
    

    【讨论】:

    • graphql-java 16.2 中没有 GraphQLQueryResolver 或 GraphQLMutationResolver。我的印象是 我必须 自定义 DataWiring 以获取要映射的东西。我认为这个问题在 16.2 变成了 GraphQLQueryResolver 和 GraphQLMutationResolver 的替代品。我熟悉这些,他们对自动类型解析做了。我想我在这里很努力。
    • 是的。这行得通,但是,哎呀。我必须得到那些 graphql-java-tools 或者一些东西来摆脱那个 DataWiring 并进入一些更自动映射的东西。我正在处理 Spring 的docs.spring.io/spring-graphql/docs/1.0.0-M1/reference/html/…,它看起来非常不完整。他们正试图获得一些基于注释的东西,但他们还没有。无论如何,谢谢你的线索。我已解锁。
    猜你喜欢
    • 1970-01-01
    • 2016-08-11
    • 2018-02-20
    • 2022-08-20
    • 1970-01-01
    • 2021-10-24
    • 2021-03-08
    • 2016-11-25
    • 2012-08-29
    相关资源
    最近更新 更多