Skip to content

Raise default ingest consumer concurrency to 8 loops per process #SUPERLOG - #530

Closed
superlog-app[bot] wants to merge 1 commit into
mainfrom
superlog/ingest-consumer-concurrency-default
Closed

superlog-app[bot] wants to merge 1 commit into
mainfrom
superlog/ingest-consumer-concurrency-default

Conversation

@superlog-app

@superlog-app superlog-app Bot commented Oct 9, 2026 •

Copy link
Copy Markdown
Contributor

Summary

The ingest queue message.age_ms histogram averaged 212 s (~3.5 min) during the Oct 9 incident, a 3.16× spike over the 67 s baseline. Delivery duration rose only 5%, ruling out ClickHouse slowness — the extra latency was pure queue-wait time caused by the consumer not draining fast enough.

Root cause

Each consume loop follows a blocking batch pattern: it calls ReceiveMessage(MaxNumberOfMessages=10), awaits Promise.all(processMessage × 10), then deletes and loops. This means throughput per loop is bounded by batchSize / per-batch-insert-time = 10 / 2.5 s = 4 msg/s. With the previous default of 4 concurrent loops per process, one process caps at 16 msg/s, and any task disruption (rolling deploy, OOM kill) reduces capacity proportionally with no headroom.

The ClickHouseIngestWriter coalesces all concurrent insert() calls within a batchLingerMs window into one ClickHouse INSERT, so raising the loop count from 4 to 8 doesn't increase the number of ClickHouse inserts — it doubles how many SQS messages are coalesced into each insert, doubling per-task throughput (80 messages / 2.5 s = 32 msg/s per process).

Fix

  • Raise DEFAULT_CONSUMER_CONCURRENCY from 4 to 8.
  • Update .env.example to match.
  • Add a test asserting the new default is applied when INGEST_QUEUE_CONSUMER_CONCURRENCY is not set (the existing bounds test at ≥ 32 → 32 is unchanged).

Deployment-side environments that set INGEST_QUEUE_CONSUMER_CONCURRENCY explicitly are unaffected by this default change.


Was this PR helpful? Leave feedback — goes straight to the Superlog team.


Summary by cubic

Raises the default ingest consumer concurrency from 4 to 8 SQS receive loops per process so the queue drains fast enough under load. During the Oct 9 incident, ingest queue message age averaged 3.5 minutes (3.16× the 67 s baseline) while delivery duration rose only 5%, showing the bottleneck was queue-wait time, not ClickHouse.

ClickHouseIngestWriter already coalesces concurrent inserts within a batchLingerMs window, so doubling the loops doubles the messages coalesced per insert rather than adding ClickHouse insert overhead. Deployments that set INGEST_QUEUE_CONSUMER_CONCURRENCY explicitly keep their current value; the change also updates .env.example and adds a test asserting the new default.

Written for commit 4a8ecb0. Summary will update on new commits.

View guided diff Turn on auto-fix

…ERLOG

Delivery-Id: c4d698a9bcf07fd4d191240de5021ec52640e8ffaaab5b1ba958addc6d12ccfc
Delivery-Base: main
@superlog-app superlog-app Bot closed this Oct 24, 2026
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

1 participant