Skip to content

sink: make sink statistics consistent and flush-aware - #5801

Open
3AceShowHand wants to merge 14 commits into
pingcap:masterfrom
3AceShowHand:statistics-sink-unify
Open

sink: make sink statistics consistent and flush-aware#5801
3AceShowHand wants to merge 14 commits into
pingcap:masterfrom
3AceShowHand:statistics-sink-unify

Conversation

@3AceShowHand

@3AceShowHand 3AceShowHand commented Jul 29, 2026

Copy link
Copy Markdown
Collaborator

What problem does this PR solve?

Sink statistics were inconsistent across sink implementations:

  • Write-byte statistics used encoded or output payload sizes and could be recorded before an asynchronous downstream write completed.
  • MySQL affected rows could be recorded before the transaction committed.
  • The sink type label split statistics for one changefeed into backend-specific series.
  • Statistics-owned Prometheus collectors were exported from pkg/metrics.

Issue Number: close #5820

What is changed and how it works?

  • Carry the original DML event size through the MQ and cloud-storage pipelines.
  • Record batch rows and write bytes only after the downstream write succeeds; Kafka and Pulsar update them from the asynchronous completion callback.
  • Record MySQL affected rows only after a successful transaction commit.
  • Remove the per-sink type label and obsolete duplicate sink metrics, and update the built-in Grafana dashboards.
  • Move Statistics and its private Prometheus collectors to pkg/statistics; expose New and InitMetrics as the package entry points.

Check List

Tests

  • Unit test

Questions

Will it cause performance regression or break compatibility?

No performance regression is expected. The change adds constant-size bookkeeping and records metrics from existing completion callbacks.

Do you need to update user documentation, design documentation or monitoring documentation?

The built-in Grafana dashboards are updated. No user or design documentation change is required.

Release note

None

Summary by CodeRabbit

  • New Features
    • Improved sink statistics consistency across Blackhole, Cloud Storage, Kafka, MySQL, and Pulsar.
    • DML processing now records write activity more accurately, including affected-row details.
  • Bug Fixes
    • Refined batch execution/error tracking for message-based sinks.
    • Fixed write-bytes and post-flush metric calculations to reflect the correct values.
  • Documentation
    • Updated Grafana dashboards and PromQL queries for more reliable sink row-rate, byte-rate, and error/DDL counting.

@ti-chi-bot ti-chi-bot Bot added do-not-merge/needs-linked-issue release-note Denotes a PR that will be considered when it comes time to generate release notes. labels Jul 29, 2026
@ti-chi-bot

ti-chi-bot Bot commented Jul 29, 2026

Copy link
Copy Markdown

[APPROVALNOTIFIER] This PR is NOT APPROVED

This pull-request has been approved by:
Once this PR has been reviewed and has the lgtm label, please assign wlwilliamx for approval. For more information see the Code Review Process.
Please ensure that each of them provides their approval before proceeding.

The full list of commands accepted by this bot can be found here.

Details Needs approval from an approver in each of these files:

Approvers can indicate their approval by writing /approve in a comment
Approvers can cancel approval by writing /approve cancel in a comment

@ti-chi-bot ti-chi-bot Bot added the size/M Denotes a PR that changes 30-99 lines, ignoring generated files. label Jul 29, 2026
@coderabbitai

coderabbitai Bot commented Jul 29, 2026

Copy link
Copy Markdown
Contributor

Review Change Stack

Note

Reviews paused

It looks like this branch is under active development. To avoid overwhelming you with review comments due to an influx of new commits, CodeRabbit has automatically paused this review. You can configure this behavior by changing the reviews.auto_review.auto_pause_after_reviewed_commits setting.

Use the following commands to manage reviews:

  • @coderabbitai resume to resume automatic reviews.
  • @coderabbitai review to trigger a single review.

Use the checkboxes below for quick actions:

  • ▶️ Resume reviews
  • 🔍 Trigger review
📝 Walkthrough

Walkthrough

The PR moves sink statistics ownership into pkg/statistics, adds flush-aware DML byte tracking, updates sink execution recording, defers MySQL affected-row metrics until commit, and aligns Grafana queries with the revised metrics.

Changes

Sink metrics and accounting

Layer / File(s) Summary
Metrics contract migration
pkg/statistics/*, pkg/metrics/*, downstreamadapter/sink/*, pkg/sink/mysql/*
Statistics construction, ownership, labels, registrations, sink integrations, and test helpers use statistics.New and *statistics.Statistics.
Flush-aware event accounting
downstreamadapter/sink/{blackhole,cloudstorage,kafka,pulsar}/*
DML events are tracked separately, while batch execution metrics are recorded after downstream callbacks or flushes without payload byte counts.
MySQL commit statistics
pkg/sink/mysql/*
Affected rows are returned from sequence execution and recorded after transaction commit.
Dashboard query alignment
metrics/grafana/*, metrics/nextgengrafana/*
Dashboards use batch-row metrics, revised label grouping, and increase for counter panels; versions advance to 42.

Estimated code review effort: 4 (Complex) | ~45 minutes

Sequence Diagram(s)

sequenceDiagram
  participant DMLSource
  participant Sink
  participant Writer
  participant Statistics
  DMLSource->>Sink: deliver DML event
  Sink->>Statistics: TrackDMLEvent
  Sink->>Writer: send or flush data
  Writer->>Statistics: RecordBatchExecution after completion
  Statistics->>Statistics: record original event bytes on PostFlush
Loading

Suggested labels: lgtm, approved

Suggested reviewers: asddongmen, hongyunyan, wk989898

Poem

I’m a rabbit counting each flow,
Bytes wait for flushes before they show.
Callbacks cheer and commits agree,
Dashboards hop in harmony.
Metrics now follow sinks true and clear.

🚥 Pre-merge checks | ✅ 4 | ❌ 1

❌ Failed checks (1 warning)

Check name Status Explanation Resolution
Docstring Coverage ⚠️ Warning Docstring coverage is 15.00% which is insufficient. The required threshold is 80.00%. Write docstrings for the functions missing them to satisfy the coverage threshold.
✅ Passed checks (4 passed)
Check name Status Explanation
Title check ✅ Passed The title clearly matches the main change: making sink statistics consistent and flush-aware.
Description check ✅ Passed The PR description includes the required issue link, change summary, tests, questions, and release note sections.
Linked Issues check ✅ Passed The changes address #5820 by unifying labels, deferring byte/row stats until flush or commit, and moving collectors into pkg/statistics.
Out of Scope Changes check ✅ Passed The dashboard updates, test rewrites, and metrics refactors are all aligned with the stated sink-statistics migration.
✨ Finishing Touches
🧪 Generate unit tests (beta)
  • Create PR with unit tests

Thanks for using CodeRabbit! It's free for OSS, and your support helps us grow. If you like it, consider giving us a shout-out.

❤️ Share

Comment @coderabbitai help to get the list of available commands.

@ti-chi-bot ti-chi-bot Bot added size/XL Denotes a PR that changes 500-999 lines, ignoring generated files. and removed size/M Denotes a PR that changes 30-99 lines, ignoring generated files. labels Jul 29, 2026
@ti-chi-bot ti-chi-bot Bot added size/XXL Denotes a PR that changes 1000+ lines, ignoring generated files. and removed size/XL Denotes a PR that changes 500-999 lines, ignoring generated files. labels Jul 29, 2026

@coderabbitai coderabbitai Bot left a comment

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Actionable comments posted: 1

🤖 Prompt for all review comments with AI agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.

Inline comments:
In `@pkg/statistics/statistics_test.go`:
- Around line 28-29: Update the statistics test setup and cleanup around
RecordBatchExecution to avoid resetting shared global metric state: use unique
label values for this test, register statistics.Close() with t.Cleanup so it
runs on assertion failure, and remove/assert only this test’s exact metric
series rather than requiring the entire collector to be empty. Preserve focused
deterministic assertions and follow the existing test guidance.
🪄 Autofix (Beta)

Fix all unresolved CodeRabbit comments on this PR:

  • Push a commit to this branch (recommended)
  • Create a new PR with the fixes

ℹ️ Review info
⚙️ Run configuration

Configuration used: Organization UI

Review profile: CHILL

Plan: Pro Plus

Run ID: c8b9cfa9-55ef-45dc-a7fc-fd8bff55d5e0

📥 Commits

Reviewing files that changed from the base of the PR and between b257afc and c33c4f9.

📒 Files selected for processing (15)
  • downstreamadapter/sink/blackhole/sink.go
  • downstreamadapter/sink/cloudstorage/dml_writers.go
  • downstreamadapter/sink/cloudstorage/sink.go
  • downstreamadapter/sink/cloudstorage/writer.go
  • downstreamadapter/sink/cloudstorage/writer_test.go
  • downstreamadapter/sink/kafka/sink.go
  • downstreamadapter/sink/mysql/sink.go
  • downstreamadapter/sink/pulsar/sink.go
  • downstreamadapter/sink/pulsar/sink_test.go
  • pkg/metrics/statistics_test.go
  • pkg/sink/mysql/mysql_writer.go
  • pkg/sink/mysql/mysql_writer_ddl_ts_test.go
  • pkg/sink/mysql/mysql_writer_test.go
  • pkg/statistics/statistics.go
  • pkg/statistics/statistics_test.go
💤 Files with no reviewable changes (1)
  • pkg/metrics/statistics_test.go
🚧 Files skipped from review as they are similar to previous changes (7)
  • pkg/sink/mysql/mysql_writer_ddl_ts_test.go
  • downstreamadapter/sink/cloudstorage/writer.go
  • downstreamadapter/sink/kafka/sink.go
  • downstreamadapter/sink/pulsar/sink.go
  • downstreamadapter/sink/cloudstorage/writer_test.go
  • downstreamadapter/sink/pulsar/sink_test.go
  • pkg/sink/mysql/mysql_writer_test.go

Comment thread pkg/statistics/statistics_test.go Outdated
@3AceShowHand 3AceShowHand changed the title metrics: statistics based on raw bytes sink: make sink statistics consistent and flush-aware Jul 29, 2026

@coderabbitai coderabbitai Bot left a comment

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Caution

Some comments are outside the diff and can’t be posted inline due to platform limitations.

⚠️ Outside diff range comments (1)
downstreamadapter/sink/pulsar/sink_test.go (1)

127-134: 🩺 Stability & Availability | 🟠 Major | ⚡ Quick win

Replace the fixed sleep with an explicit bounded completion wait.

time.Sleep(1 * time.Second) does not synchronize with the asynchronous send/callback, so slow CI can still reach the assertions before completion while fast runs always pay an unnecessary delay. Wait on the callback or producer condition with a timeout, then assert the event counts.

As per coding guidelines: **/*_test.go: Prefer focused deterministic tests; see docs/agents/testing.md before adding or changing tests.

🤖 Prompt for AI Agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.

In `@downstreamadapter/sink/pulsar/sink_test.go` around lines 127 - 134, Replace
the fixed time.Sleep in the test around ddlEvent2.PostFlush with an explicit
bounded wait tied to the asynchronous send/callback or producer completion
condition. Await completion with a timeout, then retain the existing producer
event-count and count.Load assertions; do not add an unbounded wait or unrelated
test changes.

Source: Coding guidelines

🤖 Prompt for all review comments with AI agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.

Outside diff comments:
In `@downstreamadapter/sink/pulsar/sink_test.go`:
- Around line 127-134: Replace the fixed time.Sleep in the test around
ddlEvent2.PostFlush with an explicit bounded wait tied to the asynchronous
send/callback or producer completion condition. Await completion with a timeout,
then retain the existing producer event-count and count.Load assertions; do not
add an unbounded wait or unrelated test changes.

ℹ️ Review info
⚙️ Run configuration

Configuration used: Organization UI

Review profile: CHILL

Plan: Pro Plus

Run ID: 5e46f93a-b863-4de8-8b21-902c084fcf9b

📥 Commits

Reviewing files that changed from the base of the PR and between c33c4f9 and 46c60e5.

📒 Files selected for processing (7)
  • downstreamadapter/sink/pulsar/sink_test.go
  • pkg/metrics/ddl.go
  • pkg/metrics/init.go
  • pkg/metrics/sink.go
  • pkg/sink/mysql/mysql_writer_test.go
  • pkg/statistics/metrics.go
  • pkg/statistics/statistics.go
💤 Files with no reviewable changes (2)
  • pkg/metrics/ddl.go
  • pkg/sink/mysql/mysql_writer_test.go

@3AceShowHand

Copy link
Copy Markdown
Collaborator Author

/test all

@ti-chi-bot ti-chi-bot Bot added release-note-none Denotes a PR that doesn't merit a release note. and removed do-not-merge/needs-triage-completed release-note Denotes a PR that will be considered when it comes time to generate release notes. labels Jul 29, 2026
@3AceShowHand

Copy link
Copy Markdown
Collaborator Author

/test all

@coderabbitai coderabbitai Bot left a comment

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Actionable comments posted: 2

🤖 Prompt for all review comments with AI agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.

Inline comments:
In `@downstreamadapter/sink/cloudstorage/writer.go`:
- Around line 226-239: The batch execution accounting around
RecordBatchExecution must encompass the index-file flush as well as the
data-file write and close. Move the indexFilePath write into the executor
callback, or defer RecordBatchExecution until both writes succeed, ensuring
index-write failures return an error and increment the execution error metric
while post-flush callbacks run only after the complete flush.

In `@pkg/statistics/statistics.go`:
- Around line 73-75: Prevent dry-run MySQL flushes from incrementing
ticdc_sink_write_bytes_total: in TrackDMLEvent/PostFlush accounting, or the
corresponding Writer.Flush path in pkg/sink/mysql/mysql_writer.go (225-253),
gate event.GetSize() recording behind !w.cfg.DryRun. Preserve normal metric
accounting for non-dry-run writes; update the affected sites in
pkg/statistics/statistics.go (73-75) and pkg/sink/mysql/mysql_writer.go
(225-253) as needed.
🪄 Autofix (Beta)

Fix all unresolved CodeRabbit comments on this PR:

  • Push a commit to this branch (recommended)
  • Create a new PR with the fixes

ℹ️ Review info
⚙️ Run configuration

Configuration used: Organization UI

Review profile: CHILL

Plan: Pro Plus

Run ID: 2bf0789f-b2e1-4bb1-87cd-fd1f28ec7556

📥 Commits

Reviewing files that changed from the base of the PR and between 9cea971 and e2fa057.

📒 Files selected for processing (9)
  • downstreamadapter/sink/blackhole/sink.go
  • downstreamadapter/sink/cloudstorage/writer.go
  • downstreamadapter/sink/kafka/sink.go
  • downstreamadapter/sink/mysql/sink.go
  • downstreamadapter/sink/pulsar/sink.go
  • pkg/sink/mysql/mysql_writer.go
  • pkg/sink/mysql/mysql_writer_dml_exec.go
  • pkg/statistics/statistics.go
  • pkg/statistics/statistics_test.go
🚧 Files skipped from review as they are similar to previous changes (1)
  • pkg/sink/mysql/mysql_writer_dml_exec.go

Comment thread downstreamadapter/sink/cloudstorage/writer.go
Comment thread pkg/statistics/statistics.go
@3AceShowHand

Copy link
Copy Markdown
Collaborator Author

/test all

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

release-note-none Denotes a PR that doesn't merit a release note. size/XXL Denotes a PR that changes 1000+ lines, ignoring generated files.

Projects

None yet

Development

Successfully merging this pull request may close these issues.

sink: make sink statistics consistent and flush-aware

1 participant