mongodbext plugin that bring relations between collections
Starting from mongodbext-relations@2.x
supports mongodb 3.6+ only
options:
relations
(required) - hash of fields that should be embedded, should be specified in format:{field1: field1Options, field2: fieldOptions, ...}
. Each field options could have properties:collection
(required) - instance of mongodbext collection, that should be embeddedprojection
- fields projection to embed ({_id: 1}
by default`)key
- "primary key" field (_id
by default)embedded
- function that used to create EmbeddedDocument instance (autogenerated by default)onDelete
- action that should be done on embedded document deletion, available actions: 'restrict', 'cascade', 'unset', 'pull', null ('restrict' by default)onUpdate
- action that should be done on embedded document updation, available actions:cascade
, null ('cascade' by default)
Example:
var MongoClient = require('mongodb').MongoClient;
var mongodbext = require('mongodbext');
var mongodbextRelations = require('mongodbext-relations');
MongoClient.connect('mongodb://localhost:27017/test', function(err, db) {
var authorsCol = new mongodbext.Collection(db, 'authors');
var chaptersCol = new mongodbext.Collection(db, 'chapters');
var booksCol = new mongodbext.Collection(db, 'books');
booksCol.addPlugin(mongodbextRelations, {
relations: {
'author': {
collection: authorsCol,
projection: {_id: 1, name: 1}
},
'chapters.$': {
collection: chaptersCol,
projection: {_id: 1, title: 1}
}
}
});
var author = {
_id: 1,
name: 'John Doe',
age: 42
};
var chapters = [{
_id: 1,
title: 'Chapter 1',
page: 6
}, {
_id: 2,
title: 'Chapter 2',
page: 100
}];
var book = {
_id: 1,
title: 'Book',
author: 1,
chapters: [1, 2]
};
authorsCol.insertOne(author, function() {
chaptersCol.insertMany(chapters, function() {
booksCol.insertOne(book, function(err, book) {
console.log(book);
// {
// _id: 1,
// title: 'Book',
// author: { _id: 1, name: 'John Doe' },
// chapters: [
// { _id: 1, title: 'Chapter 1' },
// { _id: 2, title: 'Chapter 2' }
// ]
// }
chaptersCol.deleteOne({_id: 1}, function(err) {
console.log(err);
// [Error: Could not delete document from collection `chapters` because it is embedded to related collection `books` in the field `chapters` of document with _id=1]
});
});
});
});
});
skipping additional db requests with trustEmbeddedValue
flag:
Relations plugin adds new trustEmbeddedValue
option to the following methods:
insertOne
insertMany
updateOne
updateMany
upsertOne
replaceOne
findOneAndUpdate
findOneAndReplace
findOneAndUpsert
Passing trustEmbeddedValue: true
will skip any additional mongodb requests for relations containig plain objects instead of identifiers. projection
is still applied, though.
This logic has two important pitfalls:
- Some complex projections are not supported. Using
trustEmbeddedValue: true
with unsupported projection will cause an error to be thrown. - Provided object is used "as is", which may result in saving outdated data. Missing fields are not fetched, but any fields not matching
projection
are dropped.