Предоставляет ли tempid Datomic уникальный идентификатор объекта?
У меня есть некоторые сомнения по поводу datomic.api/tempid
FN, который предоставляет идентификатор объекта.
Он производит некоторые long
значение, а не UUID String
а также long
64-битный, что заставляет меня задуматься о его уникальности после того, как я могу достичь лимита лонга. Было бы сложнее с UUID
вместо.
Когда я пишу некоторый код, подобный этому, я спрашиваю себя: "Достигается ли это пределом идентификатора объекта и вызывает ли проблему при добавлении новых объектов?"
@(d/transact
conn
[{:db/id (d/tempid :db.part/user)
:city/district "BEYKOZ"}])
1 ответ
Как следует из названия, tempid
предоставляет только временный идентификатор; они должны использоваться в контексте одной транзакции. Таким образом, у вас не будет исчерпания идентификаторов, если вы не превысите 2^64 новых записей в одной транзакции- и такой тип транзакции будет слишком большим для выполнения в любом случае.
Основная цель шаблонов - дать нам возможность ссылаться на вновь созданные объекты в нескольких местах транзакции.
Фактически, формат транзакции на основе карты является сокращением для векторного формата; если мы хотим создать город с парой атрибутов, то внутри Datomic делает что-то похожее на:
@(d/transact
conn
(let [city-id (d/tempid :db.part/user)]
[[:db/add city-id :city/district "BEYKOZ"]
[:db/add city-id :city/population 220364]]))
... что возможно только с каким-то общим идентификатором, но мы не знаем постоянного, вставьте ID, пока мы не отключимся от базы данных.
Tempids также позволяет нам найти эти постоянные идентификаторы с помощью возвращаемого значения transact
, глядя на карту временных идентификаторов постоянным идентификаторам. например
(let [tempid (d/tempid :db.part/user)
tx [{:db/id tempid, :city/district "BEYKOZ"}]
result @(d/transact conn tx)]
(d/resolve-tempid (:db-after result) (:tempids result) tempid))
Также стоит отметить, что начиная с Datomic 0.9.5530 вам не нужно вручную добавлять темпы к новым записям (просто оставьте :db/id
вне карты), и вы также можете использовать строки в качестве темпов. Так, например, мы могли бы переписать городскую транзакцию как:
@(d/transact
conn
[[:db/add "beykoz" :city/district "BEYKOZ"]
[:db/add "beykoz" :city/population 220364]])