PLANNED MAINTENANCE

Hello, DataStax Community!

We want to make you aware of a few operational updates which will be carried out on the site. We are working hard to streamline the login process to integrate with other DataStax resources. As such, you will soon be prompted to update your password. Please note that your username will remain the same.

As we work to improve your user experience, please be aware that login to the DataStax Community will be unavailable for a few hours on:

  • Wednesday, July 15 16:00 PDT | 19:00 EDT | 20:00 BRT
  • Thursday, July 16 00:00 BST | 01:00 CEST | 04:30 IST | 07:00 CST | 09:00 AEST

For more info, check out the FAQ page. Thank you for being a valued member of our community.


question

kavithakaran avatar image
kavithakaran asked ·

Why is a LWT read committing an uncommitted transaction?

I am reading Cassandra: The Definitive Guide, 3rd edition. It has the following text:

"The serial consistency level can apply on reads as well. If Cassandra detects that a query is reading data that is part of an uncommitted transaction, it commits the transaction as part of the read, according to the specified serial consistency level."

Why a read is committing an uncommitted transaction and doesn't it interfere with ability of the writer to rollback?

UPDATE

Subsequent questions:

When you say "It is committing a transaction from another in-flight mutation when it performed the read", do you mean that "Other in-flight transaction has progressed past the "Propose/Accept" stage by the initiator of that transaction.

If that is case,

- Can I say, once a transaction has gone past "Propose/Accept" stage, it does not matter who performs "Commit/Acknowledge" (.ie initiator of that transaction or some other read) because even the initiator of that transaction can't rollback after 3rd stage

- Regarding isolation, I thought read will return the previously committed values. but here the read seems to detect the "uncommitted read" and tries to commit it and return it. Isn't this against Isolation guarantee?

- what happens if the read was not able to commit, will it fail or will it return the previously committed values?

lightweight transactions
10 |1000 characters needed characters left characters exceeded

Up to 8 attachments (including images) can be used with a maximum of 1.0 MiB each and 10.0 MiB total.

1 Answer

Erick Ramirez avatar image
Erick Ramirez answered ·

For clarification, the serial read is not committing its own LWT write. It is committing a transaction from another in-flight mutation when it performed the read. This takes place because in Cassandra, a write is not considered successful unless it is persisted to disk.

To be clear, the serial read (in the read-before-write) is not making a new addition or update -- it is just persisting an uncommitted transaction so it can provide guarantees such as "the data exists" (IF EXISTS) or not (IF NOT EXISTS).

For example, Tom updated value X for partition Y. While that's taking place, Harry performs a conditional update for partition Y if value X exists. While checking the condition if value X exists for Harry's request, Cassandra finds that Tom's update is uncommitted so persists it to disk before confirming that value X exists.

"Committed" means that a mutation (INSERT, UPDATE or DELETE) is persisted (saved) to disk. "Uncommitted" is when a mutation is still in the process of being saved to the commitlog.

The reason this is important is that the serial read phase of the LWT read-before-write cannot say a value exists (for IF EXISTS conditionals) until that value is saved to disk. Until a mutation is written to the commitlog, it's not "successful" or doesn't exist yet (uncommitted).

If you're interested, all the phases of LWTs are explained in the blog post Lightweight Transactions in Cassandra. Cheers!

8 comments Share
10 |1000 characters needed characters left characters exceeded

Up to 8 attachments (including images) can be used with a maximum of 1.0 MiB each and 10.0 MiB total.

Thank you for the answer.


When you say "It is committing a transaction from another in-flight mutation when it performed the read", do you mean that "Other in-flight transaction has progressed past the "Propose/Accept" stage by the initiator of that transaction.


If that is case,

- Can I say, once a transaction has gone past "Propose/Accept" stage, it does not matter who performs "Commit/Acknowledge" (.ie initiator of that transaction or some other read) because even the initiator of that transaction can't rollback after 3rd stage

- Regarding isolation, I thought read will return the previously committed values. but here the read seems to detect the "uncommitted read" and tries to commit it and return it. Isn't this against Isolation guarantee?

- what happens if the read was not able to commit, will it fail or will it return the previously committed values?



0 Likes 0 · ·

@kavithakaran That's exactly the point I'm trying to make -- the "other" in-flight transaction isn't related to the LWT you're concerned about. Think of it as "there happens to be another uncommitted write" already in progress when your LWT was doing the read-before-write.

For example, Tom updated value X for partition Y. While that's taking place, Harry performs a conditional update for partition Y if value X exists.

While reading if value X exists for Harry's request, Cassandra finds that Tom's update is uncommitted so persists it to disk before confirming that value X exists. Does that make sense? :)

0 Likes 0 · ·
kavithakaran avatar image kavithakaran Erick Ramirez ♦♦ ·

`Tom updated value X for partition Y` . Cassandra finds that Tom's update is uncommitted so persists it to disk. If Tom updating value X for partition is not another LWT in progress but a normal transaction, why do we call it commit? Isn't that called read repair?

0 Likes 0 · ·
Show more comments