Fork me on GitHub
#asami
<
2022-04-04
>
simongray12:04:42

If I 1) transact some data and 2) then run another transaction after that which queries the database for the results of the previous transaction and 3) then transact based on those results, do I then need to use the db-after when querying to avoid a race condition or is it ok to use the conn everywhere?

leifericf12:04:21

I’m not skilled with Asami, nor do I know the answer to your question. I just want to commend you for asking your question clearly and succinctly. Even with my lack of knowledge, I understand precisely what you’re asking about. Asking the right questions well is a highly underrated skill.

❤️ 1
quoll12:04:41

I’m not sure of step 2. You said “transaction”, which means that you're updating data. But in step 3 you talk about transacting the data from step 2. So was step 2 a misnomer and you're only querying? Or do all 3 steps modify data?

quoll12:04:11

Also… using a connection for querying is just a shorthand for the common pattern I see where people take the latest committed database and query that. If you want to get a database State after any given transaction, you need to wait until it is complete, otherwise you’ll pick up whatever the previous version was. That's usually done by deref’ing a transaction. That will indeed have a db-after in the deref’ed value, but the latest db on the connection will have that same database as well. (Unless ANOTHER transaction completes in between)

quoll12:04:57

You probably know this, but just in case it isn't clear, the database will always be consistent. It will be a value from before a transaction, or after it has completed. It is not possible to see a state that is in-between

simongray13:04:30

I transact, then query som IDs created in the first transaction, then transact new data based on the query. I just discovered the answer by looking at the source code. I can see that the transact function derefs the result of the transact-async function.

simongray13:04:22

> You probably know this, but just in case it isn’t clear, the database will always be consistent. It will be a value from before a transaction, or after it has completed. It is not possible to see a state that is in-between Yeah, wasn’t talking about corruption, but transactions dependent on the results of other transactions.

simongray13:04:05

I was confused since a future was returned, so I figured it must be because the operation was async, but I can see that it only returns the future once the value has been deref’ed

simongray13:04:19

so technically synchronous, right?

quoll19:04:07

If it's transact then yes, it's synchronous. Mostly. You'll see that it has a timeout, and it will throw an exception if this is exceeded. If that were to happen, then the transaction will continue to run to completion, but you won't be waiting for it. (Hmm... there's no way to get the still-running future at that point. Maybe I could add it to the ex-info data)

quoll19:04:42

Why is it done this way? Because I was trying to copy Datomic. Why does Datomic do it this way? Ask Rich 🙂