Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Rework or remove CommitRecovery #623

Open
LMnet opened this issue May 27, 2021 · 10 comments
Open

Rework or remove CommitRecovery #623

LMnet opened this issue May 27, 2021 · 10 comments
Labels
enhancement New feature or request
Milestone

Comments

@LMnet
Copy link
Member

LMnet commented May 27, 2021

Recently I have worked with the CommitRecovery functionality. And I found that this part of the library is not pleasant to work with.

In particular, I faced the next issues:

  1. recoverCommitWith signature has specific bounds on F. And there is no way to add some extra bounds if I want. For example, I wanted to use log4cats and add some details about retrying inside recoverCommitWith. And at the current moment, I can't that because recoverCommitWith doesn't have a Sync bound. Overall recoverCommitWith's signature feels weird and limiting.
  2. CommitRecovery.Default is pretty nice, but not configurable.
  3. I'm using pureconfig for my configuration and I had to create a custom wrapper around CommitRecovery to make it works nicely with the pureconfig.

Also, It's debatable that this functionality should be built-in inside fs2-kafka. For me, it looks like all this retries stuff could be delegated to a specialized solution like cats-retry. And it may look more natural and composable. ATM this part is not composable: I had to overcome some difficulties to use CommitRecovery with the pureconfig, log4cats, and cats-retry.

I can suggest 2 ways of solving this:

  1. Completely remove this functionality. If the user will want to retry commit failures he can use any library and add retries on top of the commit method. As a bonus point here we will be able to remove Jitter from the library, because it uses only in CommitRecovery logic.
  2. Somehow rework this functionality. Maybe remove CommitRecovery logic from the KafkaConsumerActor and offer a CommitRecovery as an additional option on top of a commit method?
@bplommer
Copy link
Member

Sorry, I only just saw this - had my github notifications set up wrong  🤦‍♂️ I'll try give this some thought in the next few days.

@bplommer bplommer added the enhancement New feature or request label Jun 16, 2021
@bplommer
Copy link
Member

I feel like removing commit recovery as a default behaviour would be a regression in terms of robustness and approachability, so I'd like to avoid that if possible.

What if we convert CommitRecovery to be tagless final, so the bounds on F can be implementation-specific? It would mean you need Sync to instantiate ConsumerSettings with the default CommitRecovery but I don't see that as a huge problem. I think that should address your composability issue, though I'm not sure if it would address the PureConfig issue.

  1. Somehow rework this functionality. Maybe remove CommitRecovery logic from the KafkaConsumerActor and offer a CommitRecovery as an additional option on top of a commit method?

I don't quite understand what you're suggesting. But CommitRecovery could potentially be passed to the actor as part of the commit request instead of via settings - would this help with your config issue?

@LMnet
Copy link
Member Author

LMnet commented Jun 25, 2021

What if we convert CommitRecovery to be tagless final, so the bounds on F can be implementation-specific? It would mean you need Sync to instantiate ConsumerSettings with the default CommitRecovery but I don't see that as a huge problem. I think that should address your composability issue, though I'm not sure if it would address the PureConfig issue.

This will definitely not help with the pureconfig, because pureconfig implies that config creation is pure. And it sounds pretty reasonable for me — config is just pure data, why should I need some effects for creating it?

I don't quite understand what you're suggesting. But CommitRecovery could potentially be passed to the actor as part of the commit request instead of via settings - would this help with your config issue?

I suggest removing CommitRecovery from the actor logic and move it to the commit method. Like this:

def commit(recovery: CommitRecovery = CommitRecovery.Default): F[Unit]

Also, I found a few other options:

  1. Simplify CommitRecovery to a boolean flag. And make the interface itself private. If the user will have some custom logic, he will have to disable commit recovery and add his custom solution.
  2. Make CommitRecovery.Default configurable and move its config to a ConsumerSettings. Like this:
case class CommitRecoveryConfig(
  enabled: Boolean,
  maxAttempts: Int,
  maxRetryingTime: FiniteDuration
)

And make the CommitRecovery interface private too.

The main idea here is to hide the CommitRecovery interface because it's too limiting. In case of any custom need, users will have to disable CommitRecovery by a boolean flag and add any logic he wants.

I don't think that we need to evolve CommitRecovery to something more useful and complex. There are other libraries specific to that.

@bplommer
Copy link
Member

bplommer commented Jul 15, 2021

Ok, your first suggestion sounds reasonable to me. What do you think @vlovgr?

@vlovgr
Copy link
Contributor

vlovgr commented Jul 15, 2021

I agree on removing CommitRecovery and Jitter, but would like to keep the default functionality with an option to disable or configure it.

@bplommer bplommer added this to the v3.0.0 milestone Jul 16, 2021
@LMnet
Copy link
Member Author

LMnet commented Jul 29, 2021

@vlovgr just to clarify — it's option 3, right?

@bplommer
Copy link
Member

I suggest removing CommitRecovery from the actor logic and move it to the commit method. Like this:

def commit(recovery: CommitRecovery = CommitRecovery.Default): F[Unit]

This was the one I was in favour of - @vlovgr were you thinking this or reducing it to a boolean flag?

@vlovgr
Copy link
Contributor

vlovgr commented Aug 22, 2021

That option sounds good to me. 👍

@LMnet
Copy link
Member Author

LMnet commented Aug 24, 2021

@vlovgr I'm sorry, but I'm still don't understand which is your favorite option.

Thinking a bit about this recently and I concluded that the boolean flag is the best option. Moving CommitRecovery to a commit method (option 2) will not solve problems with the CommitRecovery itself. It will still be a poor implementation of retry logic.

@vlovgr
Copy link
Contributor

vlovgr commented Aug 24, 2021

Long-term (at least new major release) we should get rid of CommitRecovery completely and use a boolean flag (or some basic customization options). But short-term, we're a bit more limited, hence moving it to commit sounds like a reasonable alternative.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
enhancement New feature or request
Development

No branches or pull requests

4 participants