首页 文章

GraphQl中的动态(唯一)对象

提问于
浏览
12

我在看graphql . 是否可以定义具有任意属性的对象?假设我有一些数据:

editOptions : { boxes : 3 , size : { width: 23,height:32} , color: #434343 }, etc...}

这是在:

{ ... , box : { editOptions : {...} }, ... }

假设editOptions永远不会具有相同的结构,有时对于获得颜色没有用,例如sakes . 在mongoose中,可以将类型定义为:

editOptions:{}

这些editOptions通常对每个框都是唯一的 . 有些属性是共享的,但大多数都是唯一的 .

所以我的问题是,有没有办法做到这一点?或者这是不好的做法,我应该改变我的模型 .

谢谢 .

3 回答

  • 1

    使用 GraphQLScalarType ,只需实现它:

    import { GraphQLScalarType } from 'graphql/type';
    import { GraphQLError } from 'graphql/error';
    import { Kind } from 'graphql/language';
    
    const ObjectType = new GraphQLScalarType({
      name: 'ObjectType',
      serialize: value => value,
      parseValue: value => value,
      parseLiteral: (ast) => {
        if (ast.kind !== Kind.OBJECT) {
          throw new GraphQLError(
            `Query error: Can only parse object but got a: ${ast.kind}`, 
            [ast],
          );
        }
        return ast.value;
      },
    });
    
    const ReturnType = new GraphQLObjectType({
      name: 'ReturnType',
      fields: {
        // ...
        editOptions: { type: ObjectType },
        // ...
      },
    });
    
  • 6

    你有两个选择 .

    1.界面

    如果 editOptions 可能因类型而异,但对于该特定类型是一致的,则可以使用Interfacenode.js example) .

    假设你有两个物体,一个盒子和一个球体 . 您可以定义两个实现的对象接口:

    interface Object
    type Box implements Object {
      editOptions: BoxOptions
    }
    type BoxOptions {
      boxes: Int,
      size: ...,
      color: ...
    }
    type Sphere implements Object {
      editOptions: SphereOptions
    }
    type SphereOptions {
      spheres: Int,
      ...
    }
    type Query {
      objects: [Object]
    }
    

    在您的查询中,您将返回 Object ,以及基于每种类型的请求选项:

    query Query {
      objects(filter: "...") {
        ... on Box {
          editOptions {
            boxes
            size
          }
        }
        ... on Sphere {
          editOptions {
            spheres
          }
        }
      }
    }
    

    在返回的JSON中,框将在 editOptions 下具有 boxessize 字段,并且球体将具有 spheres .

    有时候没有颜色有用

    如果对于某些您没有颜色的框,该字段将只是空(但仍存在于模式中) .

    2. JSON

    如果 editOptions 可以真正变量,您可以将该字段定义为String,并通过序列化JSON发送 . 您将丢失所有类型验证,但结构对于每个对象可以完全任意 . 只需确保您的客户了解如何处理它 .

  • 9

    尝试GraphQL.js的JSON标量类型:graphql-type-json . 这对我很有效 .

    将SDL与GraphQL工具一起使用时,将GraphQLJSON定义为模式中适当标量类型的解析器:

    import { makeExecutableSchema } from 'graphql-tools';
    import GraphQLJSON from 'graphql-type-json';
    
    const typeDefs = `
      scalar JSON
    
      type MyType {
        editOptions: JSON
      }
    `;
    
    const resolvers = {
      JSON: GraphQLJSON,
    };
    
    export default makeExecutableSchema({ typeDefs, resolvers });
    

    您还可以在以编程方式构造的架构中使用它 .

    查看more details on this package

相关问题