Fork me on GitHub

retracting facts is equivalent to asserting those facts are no longer true. Excision is a painful surgery that changes the past (not without trace. Datoms about excisions are un-excisable and are retained)


I'm looking for a way to query the most recent transaction that has changed a specific entity. What would be the best way to achieve this?


when I make transactions, I add user id and other information to the tx, and then I'd like to show "Last changed by <user> at <time>" on frontend


@jarppe Like this?

[:find ?user ?updated-at
 :in $ ?e
 :where [?e _ _ ?t]
 		[(max ?t) ?last-txn]
 		[?last-txn :user/id ?user]
 		[?last-txn :db/txInstant ?updated-at]]


By "changed a specific entity", I hope you mean, changed an attribute of the entity directly, and not transitively changed something owned by an entity.


If you're looking at something like "changed an attribute on this entity, or another entity that this entity owns" for some definition of owns, take a look at this talk by the folks at Nubank. EDIT: The above does not work. I was mistaken. Sorry for the noise.


Thanks @jaihindh.reddy, that's exactly what I'm looking for


BTW, a side note, thanks a lot for the talk about lupapiste. Is the "state machines with guards" approach documented or available as a library somewhere?


Did you test this? I’m Pretty sure that “max ?t” is not doing what you think it is. You can’t perform aggregations in datalog where clauses

💥 10

Wow. didn't test it. Thanks for clarifying this.


you can either introduce a nested query or you can process the results


Do you have any idea what's the performance with (max ?t)?


I just setup my ions recently. Am a Datomic neophyte. Never used at work or in anger. So sorry, no idea 😄


I have a case: I have item and I have state of my item changed by a sort of events. For example state = amout of items then I have update on my state that the state is equal 7 (for example it was 10) cool...that update was with timestamp 1234, next I am getting next event which should be done earlyer so the state was 8 with timestamp 1233. Is it possible to put something in the past of my item? I would like to put 8 before 7 without changing 7 as my actual state value.


I understand that I can not remove anything from Datomic database (which it super cool) but can I add new states as a past of my actual state ? 🙂

Ben Hammond13:01:47

it is only possible to assert new data

Ben Hammond13:01:59

it is not possible to assert old data

Ben Hammond13:01:03

it might be a clue that you need a model 'data insertion as-of` as a data item in you domain

Ben Hammond13:01:50

rather than expecting to use the datomic :db/txInstant timestamp, which records the actual time the data was transacted into datomic

Ben Hammond13:01:03

(I don't have a time machine - time only moves forwards for me. I assume that's the same for most people here)


It is a little bit complicated. Those events are from third party API. It is possible that "cancel" event which is cancelling an offer will be delivered faster then "trade" event (last trade before "cancel"). At the end I have to have all of those "change state" events in a right order in my db because I have to render a list of active orders with their actual state. But at the end I can ask datomic to give me only actual orders with the good state asking for the "last" state from each of my items?

Joe Lane15:01:41

You need to model time as a first class attribute on your “trade”s. There are two different time models here. There is the logical time (datomic’s time) and then there is temporal time (information about your domain). This will allow you to add facts about things that happened in the past.

Joe Lane15:01:22

Datomic’s logical time is extremely helpful for debugging, operations, and verifying why decisions were made.

Joe Lane15:01:18

I’ve learned not to try and gather domain information from the mechanics of how datomic stores the information. You could consider them two different concerns.


Great. Now I see. Thank you @U0CJ19XAM and @U793EL04V!