thanos-io/thanos · error
could not group metadata for compaction
Error message
could not group metadata for compaction
What it means
After metas are synced, grouper.Groups(metas) groups block metadata by their compaction group (resolution + external labels). If grouping fails, the progress worker returns 'could not group metadata for compaction'. The default BaseGrouper errors when blocks in the same group would be incompatible — typically when duplicate blocks with identical labels and resolution but conflicting compaction ranges exist.
Solutions
- Run 'thanos tools bucket verify' to identify duplicate/overlapping blocks in the affected group.
- Mark the redundant blocks for deletion (deletion-mark.json) or repair via 'thanos tools bucket repair --mark-logical-deleted'.
- Ensure exactly one compactor runs per bucket to prevent future duplicates.
- Fix Prometheus external_labels so each source produces a unique label set.
Example fix
// before // duplicate blocks with same labels cause Groups() to fail // after thanos tools bucket repair --objstore.bucket=thanos --mark-logical-deleted thanos compact --data-dir=/var/thanos/compact --objstore.bucket=thanos
Defensive patterns
Strategy: validation
Validate before calling
// Detect duplicate groups client-side before compaction
seen := map[string]struct{}{}
for _, m := range metas {
key := m.Thanos.Labels.String() + fmt.Sprintf("/%d", m.Thanos.Resolution)
if _, dup := seen[key]; dup {
log.Printf("duplicate compaction group: %s", key)
}
seen[key] = struct{}{}
} Try / catch
groups, err := grouper.Groups(metas)
if err != nil {
if errors.Is(err, base.ErrGroupPermission) || errors.Is(err, base.ErrGroupNotFound) {
// duplicate/overlapping blocks: run bucket verify + repair, then alert
alertDuplicateBlocks(err)
}
return errors.Wrapf(err, "could not group metadata for compaction")
} Prevention
- Run exactly one compactor per bucket.
- Backfill historical blocks with unique external labels and non-overlapping time ranges.
- Keep Prometheus external_labels stable — changing them mid-stream creates duplicate groups.
- Schedule 'thanos tools bucket verify' regularly.
When it happens
Trigger: grouper.Groups(metas) returns ErrGroupPermission (duplicate compaction group) or ErrGroupNotFound; in practice: two blocks with identical Thanos external labels and resolution whose time ranges overlap or duplicate.
Common situations: Two compactors running concurrently on the same bucket produced duplicated/overlapping blocks; backfilled historical blocks were pushed with the same labels; Prometheus labels changed mid-stream so two blocks claim the same group.
Related errors
- create bucket compactor
- compaction
- critical error detected
- error executing compaction
- could not calculate compaction progress
AI-assisted analysis of thanos-io/thanos@35b8b99117 (2026-09-07).
Data as JSON: /api/errors/0bacaead325d828e.
Report an issue: GitHub.
Appendix: source
Thrown at cmd/thanos/compact.go:666
return runutil.Repeat(conf.progressCalculateInterval, ctx.Done(), func() error {
if err := sy.SyncMetas(ctx); err != nil {
// The RetryError signals that we hit an retriable error (transient error, no connection).
// You should alert on this being triggered too frequently.
if compact.IsRetryError(err) {
level.Error(logger).Log("msg", "retriable error", "err", err)
compactMetrics.retried.Inc()
return nil
}
return errors.Wrapf(err, "could not sync metas")
}
metas := sy.Metas()
groups, err := grouper.Groups(metas)
if err != nil {
return errors.Wrapf(err, "could not group metadata for compaction")
}
if err = ps.ProgressCalculate(ctx, groups); err != nil {
return errors.Wrapf(err, "could not calculate compaction progress")
}
retGroups, err := grouper.Groups(metas)
if err != nil {
return errors.Wrapf(err, "could not group metadata for retention")
}
if err = rs.ProgressCalculate(ctx, retGroups); err != nil {
return errors.Wrapf(err, "could not calculate retention progress")
}
if !conf.disableDownsampling {
groups, err = grouper.Groups(metas)
if err != nil {View on GitHub (pinned to 35b8b99117)