apache / apache/pulsar-client-go

[PIP] Add `StartPaused` option to `ConsumerOptions`

Open
#1,508 2 comments 0 reactions 0 assignees View on GitHub
Dominant language
Go
Stars
745
Forks
389
Avg merge
3d 20h
Merged PRs (30d)
3

Description

Depends on #1504 (adds `Pause()` / `Resume()` / `Paused()`). Related: #429.

With `Pause()` from #1504, there's a small gap that can't be avoided: between `Subscribe()`
returning and the new `Pause()` call, the consumer has already asked the broker for messages and may have pulled some. So there's no way to start a consumer that is paused from the very first moment.
`StartPaused` closes that gap: the consumer comes up paused and doesn't ask the broker for anything until a user calls `Resume()`.

Java has this on the builder:
```java
ConsumerBuilder startPaused(boolean startPaused);
```
The consumer starts paused, and the setting is passed down to every internal consumer (including topics discovered later), so it's race-free.

### Proposed Go API

One new option, no interface change:
```go
// ConsumerOptions
// StartPaused, if true, creates the consumer in the paused state: it sends no flow
// permits until Resume() is called. Default false.
StartPaused bool
```
After `Subscribe()`, `Paused()` returns true until a user calls `Resume()`.

- Pass the option down to the partition consumer and set its paused flag before it starts, so the very first connect sends no permits. #1504 already handles "paused at connect" (it holds the initial grant and flushes it on the first Resume()), so no new mechanism is needed.
- Set the paused flag on the top-level consumer at creation, so `Paused()` is correct and
new children inherit it.
- With this in place, regex and partitioned consumers can create new children already paused instead of pausing them right after creation (#1504's current approach, which has a tiny race window). This closes that race and matches Java.

### Edge cases to test

- `StartPaused`: true, produce messages, `Receive` with a timeout → nothing arrives; after `Resume()` → all messages arrive.
- `Paused()` is true right after `Subscribe`.
- Partitioned, multi-topic, and regex consumers all come up paused, including topics discovered later.

### Are you willing to submit a PR?

- [x] I'm willing to submit a PR!

Contributor guide

Open the contributing guide

Research direction

Start with ConsumerOptions, Subscribe, and the pause/resume behavior from #1504; trace option propagation through partitioned, multi-topic, and regex consumer creation. Done means StartPaused prevents messages before Resume(), Paused() is true immediately after Subscribe(), and newly discovered children also start paused.

Written by the indexing model from the issue text.

Assessment

Tech stack
go
Domain
api, distributed-systems
Issue type
Feature
Difficulty
4/5
Estimated time
3-5 days
Activity status
Quiet
Clarity
Mostly clear
Newbie friendliness
52/100

Get new issues in your inbox

A short digest of beginner-friendly GitHub issues.