Отношение один ко многим в Datomic
Допустим, у меня есть данные, которые выглядят так:
Author (id: 5) {
name: "Mercy",
blogs: [1, 2]
}
Blog (id: 1) {
title: "Hello blog"
}
Blog (id: 2) {
title: "Hello blog second"
}
Я хочу найти автора по имени и по всем заголовкам их блогов и по количеству блогов. Пока у меня есть
[:find ?blogs ?c
:where
[?e :name "Mercy"]
[?e :blogs ?blogs]
[(count ?blogs) ?c]
]
Я смог получить только общее количество блогов. Как я могу получить название блога, используя только запросы данных? У меня также не может быть отношения принадлежащих к сущности блога.
Обновить
"автор / блоги" имеет схему, которая выглядит следующим образом:
{
:db/ident :blog
:db/valueType :db.type/ref
:db/cardinality :db.cardinality/many
}
2 ответа
Это просто
[:find ?e (count ?b)
:where
[?e :name "Mercy"]
[?e :blogs ?b]]
Это будет работать, даже если вы удалите имя автора, тогда вы получите "карту" автора → количество блогов
[:find ?e ?n (count ?b)
:where
[?e :name ?n]
[?e :blogs ?b]]
Не забудьте, что эти запросы работают эффективно :name
должен быть проиндексирован (:db/index true
в схеме).
Но если вопрос так прост, я бы порекомендовал пройтись по API сущностей, он должен быть гораздо более эффективным:
(-> (d/entity db [:name "Mary"])
(:blogs)
(count))
Для поиска ссылок на работу ((d/entity db [:name "Mary"])
), вам нужно будет указать :name
как уникальный атрибут в схеме
Вы можете получить :title
от сущностей после извлечения всех атрибутов сущности:
[:find [(pull ?blogs '[:title]) ...] ?count
:where
[?e :name "Mercy"]
[?e :blogs ?blogs]
[(count ?blogs) ?count]
Дайте мне знать, если это работает.