Ассоциация
Прямой подкласс:
Создание ассоциаций в sequelize выполняется вызовом одной из функций belongsTo / hasOne / hasMany / belongsToMany для модели (источника) и указанием другой модели в качестве первого аргумента функции (цели).
- hasOne - добавляет внешний ключ в цель и единственные миксины ассоциаций в источник.
- belongsTo - добавляет внешний ключ и единственные миксины ассоциаций в источник.
- hasMany - добавляет внешний ключ в цель и множественные миксины ассоциаций в источник.
- belongsToMany - создаёт N:М ассоциацию со вспомогательной таблицей и добавляет множественные миксины ассоциаций в источник. Вспомогательная таблица создаётся со столбцами sourceId и targetId.
Создание ассоциации добавит ограничение внешнего ключа к атрибутам. Все ассоциации используют CASCADE при обновлении и SET NULL при удалении, за исключением n:m, которая также использует CASCADE при удалении.
При создании ассоциаций можно указать псевдоним с помощью опции as. Это полезно, если одна и та же модель ассоциирована дважды или вы хотите, чтобы ваша ассоциация называлась иначе, чем целевая модель.
Например, рассмотрим случай, когда пользователи имеют много фотографий, одна из которых является их аватаркой. Все фотографии имеют userId, но кроме этого модель пользователя также имеет profilePictureId, чтобы легко загрузить аватарку пользователя.
User.hasMany(Picture)
User.belongsTo(Picture, { as: 'ProfilePicture', constraints: false })
user.getPictures() // gets you all pictures
user.getProfilePicture() // gets you only the profile picture
User.findAll({
where: ...,
include: [
{ model: Picture }, // load all pictures
{ model: Picture, as: 'ProfilePicture' }, // load the profile picture.
// Notice that the spelling must be the exact same as the one in the association
]
})
Для полного контроля над столбцом внешнего ключа, добавляемым sequelize, можно использовать опцию foreignKey. Она может быть строкой, определяющей имя, или типом объекта, эквивалентным тем, которые передаются в sequelize.define.
User.hasMany(Picture, { foreignKey: 'uid' })
Столбец внешнего ключа в Picture теперь будет называться uid вместо значения по умолчанию userId.
User.hasMany(Picture, {
foreignKey: {
name: 'uid',
allowNull: false
}
})
Это указывает, что столбец uid не может быть null. В большинстве случаев это уже покрывается ограничениями внешнего ключа, которые sequelize создаёт автоматически, но может быть полезно в случаях, когда внешние ключи отключены, например, из-за циклических ссылок (см. constraints: false ниже).
При получении связанных моделей можно ограничить запрос, чтобы загрузить только некоторые модели. Эти запросы записываются так же, как и запросы к find/findAll. Чтобы получить только фотографии в формате JPG, можно сделать следующее:
user.getPictures({
where: {
format: 'jpg'
}
})
Существует несколько способов обновления и добавления новых ассоциаций. Продолжая наш пример с пользователями и фотографиями:
user.addPicture(p) // Add a single picture
user.setPictures([p1, p2]) // Associate user with ONLY these two picture, all other associations will be deleted
user.addPictures([p1, p2]) // Associate user with these two pictures, but don't touch any current associations
Не нужно передавать весь объект в функции ассоциаций, если у вашей связанной модели есть один первичный ключ:
user.addPicture(req.query.pid) // Here pid is just an integer, representing the primary key of the picture
В приведённом выше примере указано, что пользователь принадлежит своей аватарке. По сути, это может не иметь смысла, но поскольку мы хотим добавить внешний ключ к модели пользователя, это делается таким образом.
Обратите внимание, как мы также указали constraints: false для аватары. Это связано с тем, что мы добавляем внешний ключ от пользователя к фотографии (profilePictureId) и от фотографии к пользователю (userId). Если бы мы добавили внешние ключи к обоим, это создало бы циклическую зависимость, и sequelize не знал бы, какую таблицу создавать первой, так как пользователь зависит от фотографии, а фотография зависит от пользователя. Такие проблемы распознаются sequelize до синхронизации моделей с базой данных, и вы получите ошибку типа Error: Cyclic dependency found. 'users' is dependent of itself. Если вы столкнётесь с этим, вы должны либо отключить некоторые ограничения, либо пересмотреть свои ассоциации полностью.
Краткое описание членов
| Общедоступные члены | ||
|---|---|---|
| общедоступно | associationType: string Тип ассоциации. | |
| общедоступно | ||
| общедоступно | ||
Общедоступные члены
общедоступно associationType: string источник
Тип ассоциации. Один из HasMany, BelongsTo, HasOne, BelongsToMany
Copyright © 2014–present Sequelize contributors
Licensed under the MIT License.
https://sequelize.org/v4/class/lib/associations/base.js~Association.html