Java中没有联合体union,应该如何实现union功能呢

Posted

tags:

篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了Java中没有联合体union,应该如何实现union功能呢相关的知识,希望对你有一定的参考价值。

Java中没有联合体union,应该如何实现union功能呢

Java不需要union,如果你想改变类型的话,那么声明一个Object类型不就就行了,但是个人觉得这样很麻烦,你用的时候还要转型,如果转型错误会抛出异常追问

联合体,就是给其中的哪一个赋值就是哪一个,其他就不存在了。
谢谢你,我已经解决了,不是这里的问题

参考技术A Java中就用对象啊
class Union
...

Graphql没有为接口/联合定义解析器 - java

【中文标题】Graphql没有为接口/联合定义解析器 - java【英文标题】:Graphql no resolver definied for interface/union - java 【发布时间】:2019-06-12 14:21:16 【问题描述】:

我在graphql 中使用此方法添加解析器时遇到问题:

@RestController
@RequestMapping("/api/dictionary/")
@RequiredArgsConstructor(onConstructor = @__(@Autowired))
public class DictionaryController 
    @Value("classpath:items.graphqls")
    private Resource schemaResource;
    private GraphQL graphQL;
    private final DictionaryService dictionaryService;

    @PostConstruct
    public void loadSchema() throws IOException 
        File schemaFile = schemaResource.getFile();
        TypeDefinitionRegistry registry = new SchemaParser().parse(schemaFile);
        RuntimeWiring wiring = buildWiring();
        GraphQLSchema schema = new SchemaGenerator().makeExecutableSchema(registry, wiring);
        graphQL = GraphQL.newGraphQL(schema).build();
    

private RuntimeWiring buildWiring() 
    DataFetcher<List<DictionaryItemWithParentDto>> fetcher6 = dataFetchingEnvironment -> dictionaryService.getClaimSubType();

        return RuntimeWiring.newRuntimeWiring()
                .type("Query", typeWriting ->
                   typeWriting
                    .dataFetcher("getClaimSubType", fetcher6)
                    )
                .build();
    


public List<DictionaryItemWithParentDto> getClaimSubType() 
    return dictionaryService.getClaimSubType();
   
  

items.graphqls文件内容:

type Query 
    getClaimSubType: [DictionaryItemWithParentDto]


type DictionaryItemWithParentDto 
    code: String!
    name: String
    parents: [DictionaryItemDto]


type DictionaryItemDto 
    code: String!
    name: String
    description: String

在 java 中,我有 Vehicle 接口和两个实现它的类:AirplaneCar。当我将这一行添加到架构时:

union SearchResult = Airplane | Car

我收到以下错误:

There is no type resolver defined for interface / union 'Vehicle' type, There is no type resolver defined for interface / union 'SearchResult' type]

我不知道如何处理它。

如果我添加:

interface Vehicle 
    maxSpeed: Int


type Airplane implements Vehicle 
    maxSpeed: Int
    wingspan: Int


type Car implements Vehicle 
    maxSpeed: Int
    licensePlate: String

我收到以下错误:

errors=[There is no type resolver defined for interface / union 'Vehicle' type]

如何使用我的方法处理这些错误?有没有其他的处理方法?

编辑

我猜添加这些代码行可以解决部分问题:

TypeResolver t =  new TypeResolver() 
    @Override
    public GraphQLObjectType getType(TypeResolutionEnvironment env) 
        Object javaObject = env.getObject();
        if (javaObject instanceof Car) 
            return env.getSchema().getObjectType("Car");
         else if (javaObject instanceof Airplane) 
            return env.getSchema().getObjectType("Airplane");
         else 
            return env.getSchema().getObjectType("Car");
        
    
;

并添加到RuntimeWiring builder 这个:

            .type("Vehicle", typeWriting ->
                    typeWriting
                            .typeResolver(t)
            )


    @PostMapping("getVehicle")
    public ResponseEntity<Object> getVehicleMaxSpeed(@RequestBody String query) 
   
        ExecutionResult result = graphQL.execute(query);
        return new ResponseEntity<Object>(result, HttpStatus.OK);
    

要求时:

query 
    getVehicle(maxSpeed: 30) 
        maxSpeed

    

我得到了maxSpeed,但是当我添加wingspan 时出现错误

Field 'wingspan' in type 'Vehicle' is undefined @ 'getVehicle/wingspan'",

我加了

getVehicle(maxSpeed: Int): Vehicle

graphqls 文件。我认为多态在这里会起作用。

【问题讨论】:

【参考方案1】:

添加这些代码行可以解决问题:

TypeResolver t =  new TypeResolver() 
    @Override
    public GraphQLObjectType getType(TypeResolutionEnvironment env) 
        Object javaObject = env.getObject();
        if (javaObject instanceof Car) 
            return env.getSchema().getObjectType("Car");
         else if (javaObject instanceof Airplane) 
            return env.getSchema().getObjectType("Airplane");
         else 
            return env.getSchema().getObjectType("Car");
        
    
;

并添加到RuntimeWiring builder 这个:

            .type("Vehicle", typeWriting ->
                    typeWriting
                            .typeResolver(t)
            )


    @PostMapping("getVehicle")
    public ResponseEntity<Object> getVehicleMaxSpeed(@RequestBody String query) 
   
        ExecutionResult result = graphQL.execute(query);
        return new ResponseEntity<Object>(result, HttpStatus.OK);
    

要求时:

query 
    getVehicle(maxSpeed: 30) 
        maxSpeed

    

我得到了maxSpeed,但是当我添加wingspan 时出现错误

Field 'wingspan' in type 'Vehicle' is undefined @ 'getVehicle/wingspan'",

我加了

getVehicle(maxSpeed: Int): Vehicle

graphqls 文件。我认为多态在这里会起作用。

如果我想要来自子类的字段,我可以这样要求它们:

query 
    getVehicle(maxSpeed: 10) 
        maxSpeed
        ... on Airplane 
        wingspan
      
        ... on Car 
        licensePlate
      
    

【讨论】:

你是如何编译这行代码的? if (javaObject instanceof Car) 这个 CAR 类是如何生成的? 正常Java类-手工制作 在不创建 Car 类的情况下有没有通用的方法? @stark 我已经检查了javaObject instanceof Map &amp;&amp; ((Map)javaObject).get("__typename") 并将类型名称直接放入映射值中。你可以做任何你想做的事情来确定 GraphQL 类型名称,给定一个值,它必须是基于具体类的(尽管它是一个非常 Java 惯用的选项)

以上是关于Java中没有联合体union,应该如何实现union功能呢的主要内容,如果未能解决你的问题,请参考以下文章

MySQLDQL之联合查询

oracle union all啥意思?

Graphql没有为接口/联合定义解析器 - java

单片机嵌入式开发中union(联合体)使用示例

C语言union的用法

如何知道为 union 设置了哪个变量值?