简体   繁体   English

序列化和响应请求GraphQL

[英]Sequelize and response request GraphQL

I try to have a response on my request GraphQL. 我尝试对我的请求GraphQL进行响应。

I tried many things but currently I have always the Sequence response, and no the Buckets response (belongs To relation). 我尝试了很多事情,但目前我始终拥有Sequence响应,而没有Buckets响应(属于To关联)。

I have 2 tables : 我有2张桌子:

Sequence [id | 序列[id | is_active] 活跃]

Bucket [id | 铲斗[id | fk_language_id | fk_language_id | fk_sequence_id | fk_sequence_id | is_active] 活跃]

model/sequence.js 模型/sequence.js

'use strict';
module.exports = (sequelize, DataTypes) => {
    // define sequence
    const Sequence = sequelize.define('sequence', {
        is_active: {type: DataTypes.BOOLEAN}
    });

    Sequence.associate = function (models) {

    models.Sequence.hasMany(models.Bucket, {
        foreignKey: 'fk_sequence_id'
    });

    return Sequence;
};

model/bucket.js 模型/bucket.js

'use strict';
module.exports = (sequelize, DataTypes) => {
    const Bucket = sequelize.define('bucket', {
        code     : {type: DataTypes.STRING},
        is_active: {type: DataTypes.BOOLEAN}
    });

    Bucket.associate = function (models) {
        models.Bucket.belongsTo(models.Language, {
            foreignKey: 'fk_language_id',
        });    

        models.Bucket.belongsTo(models.Sequence, {
            foreignKey: 'fk_sequence_id',
        });
    };

    return Bucket;
};

schema.js schema.js

  # Sequence
  type Sequence {
    id: Int!,
    code: String,
    buckets: [Bucket],
    is_active: Boolean
  }

  # Bucket
  type Bucket {
    id: Int!,
    code: String
    blocks: [Block]
    is_active: Boolean
  }

  # SequenceInput
  input SequenceInput {
    buckets: [BucketInput],
    is_active: Boolean
  }

  # BucketInput
  input BucketInput {
    code: String,
    fk_language_id: Int,
    fk_sequence_id: Int,
    is_active: Boolean
  }

  type Query {
    sequences: [Sequence]
    sequence(id: Int): Sequence

    buckets: [Bucket]
    bucket(id: Int): Bucket
  }

  type Mutation {
    createSequence(input: SequenceInput): Sequence,
  } 

Request GraphQL 要求GraphQL

mutation {
  createSequence(input: { 
    is_active: false, 
    buckets: [
      {fk_language_id: 2, code: "Test"}
    ] 
  }) {
    is_active,
    buckets {
      id,
      code
    }
  }
}

But I have this result, the Buckets doesn't load : 但是我有这个结果,Buckets没有加载:

{
  "data": {
    "createSequence": {
      "is_active": false,
      "buckets": []
    }
  }
}

my mutation : 我的突变:

...
Sequence      : {
    buckets(sequence) {
        return models.Bucket.findAll({
            where: {id: sequence.id}
        });
    },
    ...
},
...
Mutation    : {
createSequence(_, {input}) {
    let sequenceId = 0;

    // Create Sequence
    return models.Sequence.create(input)
                 .then((sequence) => {
                     sequenceId = sequence.id;
                     console.log('sequence created');
                     // Create Bucket
                     // Foreach on buckets

                     return Promise.map(input.buckets, function (bucket) {
                         bucket.fk_sequence_id = sequenceId;
                         console.log('bucket created');
                         return models.Bucket.create(bucket);
                     })

                 })
                 .then(() => {
                     console.log('load created', sequenceId);
                     return models.Sequence.findOne({
                         where  : {id: sequenceId},
                         include: [
                             {
                                 model: models.Bucket,
                                 where: { fk_sequence_id: sequenceId }
                             }
                         ]
                     }).then((response) => {
                         console.log(response);

                         return response;
                     })

                 });

},
}

The final console.log show many informations... 最终的console.log显示许多信息...

sequence {
  dataValues: 
   { id: 416,
     is_active: false,
     created_at: 2019-03-29T20:33:56.196Z,
     updated_at: 2019-03-29T20:33:56.196Z,
     buckets: [ [Object] ] },
  _previousDataValues: 
   { id: 416,
     is_active: false,
     created_at: 2019-03-29T20:33:56.196Z,
     updated_at: 2019-03-29T20:33:56.196Z,
     buckets: [ [Object] ] },
  _changed: {},
  _modelOptions: 
   { timestamps: true,
     validate: {},
     freezeTableName: true,
     underscored: false,
     paranoid: false,
     rejectOnEmpty: false,
     whereCollection: { id: 416 },
     schema: null,
     schemaDelimiter: '',
     defaultScope: {},
     scopes: {},
     indexes: [],
     name: { plural: 'sequences', singular: 'sequence' },
     omitNull: false,
     createdAt: 'created_at',
     updatedAt: 'updated_at',
     sequelize: 
      Sequelize {
        options: [Object],
        config: [Object],
        dialect: [Object],
        queryInterface: [Object],
        models: [Object],
        modelManager: [Object],
        connectionManager: [Object],
        importCache: [Object],
        test: [Object] },
     hooks: {} },
  _options: 
   { isNewRecord: false,
     _schema: null,
     _schemaDelimiter: '',
     include: [ [Object] ],
     includeNames: [ 'buckets' ],
     includeMap: { buckets: [Object] },
     includeValidated: true,
     attributes: [ 'id', 'is_active', 'created_at', 'updated_at' ],
     raw: true },
  isNewRecord: false,
  buckets: 
   [ bucket {
       dataValues: [Object],
       _previousDataValues: [Object],
       _changed: {},
       _modelOptions: [Object],
       _options: [Object],
       isNewRecord: false } ] }

Your mutation resolver returns a Promise, which resolves into a Model instance. 您的突变解析器返回一个Promise,该Promise解析为Model实例。 The promise in question is returned on this line: 有问题的诺言在以下行中返回:

return models.Sequence.create(input)

.

As such, the server will wait until that promise is resolved before passing the value forward. 这样,服务器将等待该承诺得到解决,然后再传递值。 Other actions were also waiting on that promise, but they were not the promises returned, so they will not be waited for. 其他行动也正在等待该承诺,但是它们不是承诺的返回,因此不会等待它们。

All you have to do is wait for all of your operations to finish before resolving your promise. 您要做的就是等待所有操作完成,然后再兑现您的承诺。

createSequence: async (parent, { input }) => {
  const sequence = await models.Sequence.create({
    is_active: input.is_active
  })
  if (!input.buckets) return sequence
  // You may have to modify your Sequence.buckets resolver to avoid fetching buckets again.
  sequence.buckets = await Promise.all(input.buckets.map(bucket => {
    // You can avoid these if checks by implementing stricter input types.
    // e.g. buckets: [BucketInput!]!
    if (!bucket) return null
    return models.Bucket.create({
      ...bucket,
      fk_sequence_id: sequence.id
    })
  }))
  return sequence
}

Also, make sure your Sequence.buckets resolver isn't overwriting buckets with faulty data. 另外,请确保您的Sequence.buckets解析程序不会用错误的数据覆盖存储桶。 The resolver you've provided will try to match bucket primary keys with a sequence primary key instead of matching the correct foreign keys with a primary key. 您提供的解析器将尝试将存储桶主键与序列主键匹配,而不是将正确的外键与主键匹配。

Here's a resolver that will work: 这是一个可以使用的解析器:

buckets: (parent) => (
  parent.buckets // This line may conflict with some of your code and cause problems.
  || models.Bucket.findAll({
    where: {fk_sequence_id: parent.id}
  })
)

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM