Я начинаю в Mongodb
, и, как вы знаете, этого нет relaciones
, нет joins
tablas
и т. Д.
Я пытаюсь передать реляционную диаграмму в NOSQL
. У меня есть следующие таблицы.
пользователи
id
name
Сообщения
idUserFrom
idUserTo
messages
Как видите, у таблицы messages
есть внешний идентификатор users
, как я могу его создать, хотя его нет в монго, pks
и fks
как я могу выполнить этот шаг.
Пока я создал базу данных и одну collection
со вставкой таблицы users
.
> use mongodb
switched to db mongodb
> db
mongodb
> db.users.insert({id:"1",name:"Jorge"})
WriteResult({ "nInserted" : 1 })
> show collections
users
> db.users.find().pretty();
{
"_id" : ObjectId("5c9bbc275a56aa679bb06155"),
"id" : "1",
"name" : "Jorge"
}
collections
Как я могу сделать так, чтобы это выглядело так : messages
эта таблица содержит идентификатор некоторого пользователя, который может быть idFrom
илиidTo
db.messages.find().pretty();
{
"_id" : ObjectId("5c9bbc275a56aa679bb06155"),
"idFrom" : "xxxxxxxxxx",
"idTo" : "xxxxxxxxxx",
"message" : "Hola"
}
В MongoDB существуют отношения между коллекциями. Дело в том, что Mongo является базой данных noSQL . Это означает, что он не использует язык структурированных запросов (или SQL на английском языке). Следовательно, нет такого предложения, как
SELECT * FROM table
, так как оно типично для этого языка.С другой стороны, термин « нереляционная база данных» часто путают с отсутствием отношений. Правда в том, что Mongo позволяет вам реализовывать отношения, но через нечто, известное как ссылки . Ходят даже спокойные разговоры о кардинальности отношений с теми же характеристиками, которые мы знаем в «реляционной» базе данных. Особенность Mongo (как и многих других БД noSQL ) заключается в том, что она не соответствует модели ER (Entity-Relationship) и не придерживается ее точно, поэтому ее называют нереляционной БД .
ПРОБЛЕМА
Вы хотите создать связь между двумя коллекциями Mongo. Одна коллекция, называемая пользователями , будет иметь связь с другой коллекцией, называемой сообщениями . Каждый типовой документ должен
message
иметь ссылку в двух полях на типовой документuser
.РЕШЕНИЕ
Чтобы достичь того, что мы предлагаем, мы должны создать ссылку
user
в каждом поле типа документаmessage
, где мы хотим создать связь. Mongo предлагает нам два типа ссылокСсылки на руководство
Они используются для размещения значения
_id
документа в поле другого документа. Затем, если вы хотите получить связанный документ_id
, вы должны сделать второй запрос к базе данных, используя информацию указанного значения.Предположим, мы создаем коллекцию
users
следующим образом:Если мы хотим увидеть объекты коллекции
users
, которую мы только что создали, мы будем использовать методfind()
:Мы видим, что Mongo присвоил значениям
_id
типObjectId
. Он делает это автоматически, если мы_id
явно не передаем ему значение для поля.Теперь мы создадим коллекцию
messages
и введем ссылку вручную. Достигаем этого следующим образом:(мы использовали соответствующие значения
_id
)Если мы хотим увидеть документы в коллекции,
messages
мы снова используем методfind()
:Теперь у нас есть вручную связанные документы в коллекции
messages
с документами в коллекцииusers
.Во многих случаях для нашего приложения будет достаточно этих типов ручных взаимосвязей. Однако, чтобы узнать имя или адрес электронной почты пользователя, отправившего сообщение, или пользователя, получившего сообщение, мы должны сделать второй запрос к базе данных:
В предыдущем запросе я использовал
query
({"_id" : ObjectId("5c9cce340aee604c4ab6cd08")}
) в методеfind()
, а также передалprojection
({"_id":0, "idFrom": 1}
) в качестве параметра.Если бы мы хотели сделать аналогичный запрос на SQL, его можно было бы написать так:
Вы можете найти больше информации о методе
find()
в документацииСсылки DBRef
DBRefs — это соглашение, используемое для представления документа, а не определенного (вручную) типа ссылки, подобного тому, который мы только что видели. Ссылки этого типа включают имя коллекции, к которой принадлежит документ, значение поля
_id
документа и могут включать имя базы данных, к которой принадлежит коллекция.Документ
DBRef
имеет следующий формат: (важно соблюдать порядок полей)Чтобы использовать ссылку на тип
DBRef
в нашем случае, мы можем сделать это следующим образом:Если мы сделаем запрос к нашей коллекции
messages2
, мы получим следующее:Таким образом, мы создали связь между коллекцией
messages2
и коллекцией,users
используяDBRefs
.Опять же, чтобы узнать имя или адрес электронной почты пользователя, который отправляет или получает, необходимо сделать второй запрос в базу данных.
ПРИСОЕДИНИТЬСЯ
Теперь, поскольку вопрос спрашивает, можно ли выполнять JOIN в Mongo, ответ: ДА, используя метод с именем
aggregate()
, который, как предполагает его перевод, добавляет что-то к нашему запросу. В этом случае мы можем добавить документы, связанные с в e_id
поля коллекции . Этот тип известен как . Таким образом, у нас есть способ получить данные в одном запросе.idFrom
idTo
messages
aggregation
$lookup aggregation
Простой пример этого можно увидеть в следующем запросе:
По сути, мы говорим Mongo искать документы в коллекции
users
, которые_id
соответствуют полюidFrom
e ,idTo
и добавлять их в возвращенный документ в полеsender
и полеreceiver
.В переводе на SQL это простой JOIN или, может быть, запрос типа:
Как видите, почти все, что можно сделать с помощью SQL, можно сделать и в Mongo.
Надеюсь, это тот ответ, который вы искали.