简体   繁体   English

如何在Sequelize中消除相同模型之间的多个关联之间的歧义

[英]How to disambiguate between multiple associations between the same models in Sequelize

I have three models — Book , User and Institution — which are associated to one another as follows: 我有三个模型BookUserInstitution彼此关联,如下所示:

  • Books are associated to Institutions via a Book_Institution join table (many to many relationship) 图书通过Book_Institution表与机构相关联(多对多关系)

     Book.belongsToMany(models.Institution, { through: 'Book_Institution' }) 

    and

     Institution.belongsToMany(models.Book, { through: 'Book_Institution' }) 
  • Users can be associated to Institutions in two ways: as reader or author. 可以通过两种方式将用户与机构关联:作为读者或作者。 This is done via two join tables: Author_Institution and Reader_Institution : 这是通过两个Author_Institution表完成的: Author_InstitutionReader_Institution

     Institution.belongsToMany(models.User, { through: 'Author_Institution' }) Institution.belongsToMany(models.User, { through: 'Reader_Institution' }) 

    and

     User.belongsToMany(models.Institution, { through: 'Author_Institution' }) User.belongsToMany(models.Institution, { through: 'Reader_Institution' }) 

    (Each time leaving out foreignKey for brevity.) (为简洁起见,每次都省略foreignKey 。)

I want to query the Book model to find all books that belong to an author. 我想查询Book模型来查找属于作者的所有书。 Sequelize provides the include option to easily join two associated tables. Sequelize提供了include选项,可以轻松地连接两个关联的表。 The problem I'm stuggling with is that using include as shown below defaults to the Reader_Institution association. 我与有点吃力的问题是,使用include如下所示默认为Reader_Institution关联。 How can I specify which association should be used? 如何指定应使用哪个关联?

getBooks: (obj, args, context) => {
  const { user } = context

  return Book.findAll({
    attributes: ['id', 'path'],
    include: [{
      include: [{
        attributes: ['id'],
        model: User,
        where: { id: user }
      }],
      model: Institution,
      required: true // inner join
    }]
  })
}

Thanks in advance for your help. 在此先感谢您的帮助。

I use as which allows you to reference the relationship through that alias. 我用as允许您通过该别名引用关系。

Institution.belongsToMany(models.User, { 
    through: 'Author_Institution', // many-to-many relationship table name
    as: 'AuthorInstitution' // alias
})

With your models set up this way, you can use as to to specify which relationship you want to include when querying. 通过这种方式设置模型,您可以使用as指定要在查询时包括的关系。

getBooks: (obj, args, context) => {
  const { user } = context

  return Book.findAll({
    attributes: ['id', 'path'],
    include: [{
      include: [{
        attributes: ['id'],
        model: User,
        where: { id: user },
        as: 'AuthorInstitution'
      }],
      model: Institution,
      required: true // inner join
    }]
  })
}

Also, with this methodology, it allows you you to reference the relationship data via the as , so you can do book.AuthorInstitution and it will be the value of that object. 同样,使用这种方法,它允许您通过as引用关系数据,因此可以执行book.AuthorInstitution并将其作为该对象的值。

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

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