hyperledger/fabric · error

config currently at sequence %d, cannot validate config at s

Error message

config currently at sequence %d, cannot validate config at sequence %d

What it means

This error comes from the configtx validator's Validate method. The validator maintains the current sequence number of a channel config, and every incoming ConfigEnvelope must advance the sequence by exactly one (current+1). If the submitted config's Sequence is anything else, validation is rejected with this message.

Source

Thrown at common/configtx/validator.go:172

			Sequence:     vi.sequence + 1,
			ChannelGroup: channelGroup,
		},
		LastUpdate: configtx,
	}, nil
}

// Validate simulates applying a ConfigEnvelope to become the new config
func (vi *ValidatorImpl) Validate(configEnv *cb.ConfigEnvelope) error {
	if configEnv == nil {
		return errors.Errorf("config envelope is nil")
	}

	if configEnv.Config == nil {
		return errors.Errorf("config envelope has nil config")
	}

	if configEnv.Config.Sequence != vi.sequence+1 {
		return errors.Errorf("config currently at sequence %d, cannot validate config at sequence %d", vi.sequence, configEnv.Config.Sequence)
	}

	configUpdateEnv, err := protoutil.EnvelopeToConfigUpdate(configEnv.LastUpdate)
	if err != nil {
		return err
	}

	configMap, err := vi.authorizeUpdate(configUpdateEnv)
	if err != nil {
		return err
	}

	channelGroup, err := configMapToConfig(configMap, vi.namespace)
	if err != nil {
		return errors.Errorf("could not turn configMap back to channelGroup: %s", err)
	}

	// reflect.Equal will not work here, because it considers nil and empty maps as different

View on GitHub (pinned to 2736b63f8f)

Solutions

  1. Fetch the current channel config, read its sequence number, and rebuild the update so Config.Sequence == current+1
  2. Use configtxlator/peer channel fetch config to get the latest config and recompute the update from it
  3. Check for concurrent/f duplicate submissions — the update may already have been applied
  4. If a ledger rollback desynced the sequence, restart or re-initialize the validator from the current committed block

Example fix

// before
configEnv.Config.Sequence = 5 // hard-coded, channel is at 5
// after
currentSeq := latestConfig.Sequence
configEnv.Config.Sequence = currentSeq + 1
Defensive patterns

Strategy: validation

Validate before calling

env, _ := fetchLatestConfigEnvelope(channel)
if configEnv.Config.Sequence != env.Config.Sequence+1 {
    return fmt.Errorf("rebuild update: expected seq %d, got %d", env.Config.Sequence+1, configEnv.Config.Sequence)
}

Prevention

When it happens

Trigger: Calling Validator.Validate with a ConfigEnvelope whose Config.Sequence != vi.sequence+1 — e.g. resubmitting an already-applied config, skipping a sequence, or replaying an old config update.

Common situations: Submitting a stale configtx update generated earlier against an older channel config; concurrent admin updates where one was already committed; tooling that hand-builds config envelopes with a wrong sequence number; ledger rollbacks that desync the validator's sequence.

Related errors


AI-assisted analysis of hyperledger/fabric@2736b63f8f (2026-09-04). Data as JSON: /api/errors/8055e8cb8346b019. Report an issue: GitHub.