hyperledger/fabric · error

node with id of %d doesn't exist

Error message

node with id of %d doesn't exist

What it means

VerifySignature looks up the signer's identity in the runtime config's ID-to-identities map using signature.ID. If the ID is not present — i.e. the signer is not a known consenter of the channel in the current config — this error is returned before cryptographic evaluation.

Source

Thrown at orderer/consensus/smartbft/verifier.go:148

	if block.Data == nil {
		return []types.RequestInfo{}
	}

	var res []types.RequestInfo
	for _, txn := range block.Data.Data {
		req := v.ReqInspector.RequestID(txn)
		res = append(res, req)
	}

	return res
}

// VerifySignature verifies signature
func (v *Verifier) VerifySignature(signature types.Signature) error {
	id2Identity := v.RuntimeConfig.Load().(RuntimeConfig).ID2Identities
	identity, exists := id2Identity[signature.ID]
	if !exists {
		return errors.Errorf("node with id of %d doesn't exist", signature.ID)
	}

	return v.ConsenterVerifier.Evaluate([]*protoutil.SignedData{
		{Identity: identity, Data: signature.Msg, Signature: signature.Value},
	})
}

// VerifyRequest verifies raw request
func (v *Verifier) VerifyRequest(rawRequest []byte) (types.RequestInfo, error) {
	return v.verifyRequest(rawRequest, false)
}

func (v *Verifier) verifyRequest(rawRequest []byte, noConfigAllowed bool) (types.RequestInfo, error) {
	req, err := v.ReqInspector.unwrapReq(rawRequest)
	if err != nil {
		return types.RequestInfo{}, err
	}

View on GitHub (pinned to 2736b63f8f)

Solutions

  1. Commit a config update that adds the missing node to the channel's consenters
  2. Ensure every consenter's TLS certificates are correctly listed in the channel config so its ID maps to an identity
  3. Confirm all nodes use the same config block generation; a stale node sees an outdated ID map
  4. Check for duplicate/wrong TLS certs causing unstable ID derivation
Defensive patterns

Strategy: validation

Validate before calling

rc := v.RuntimeConfig.Load().(RuntimeConfig)
if _, ok := rc.ID2Identities[signature.ID]; !ok {
    return fmt.Errorf("unknown signer id %d", signature.ID)
}

Type guard

func knownNode(rc RuntimeConfig, id uint64) bool {
    _, ok := rc.ID2Identities[id]
    return ok
}

Try / catch

if err := VerifySignature(sig); err != nil {
    if strings.Contains(err.Error(), "doesn't exist") {
        // refresh config / ignore message from removed consenter
    }
}

Prevention

When it happens

Trigger: A signature received from a node whose ID is not in the channel's current consenter set (removed consenter still signing, message from a node of another channel, or IDs diverged after a config update).

Common situations: Consenter removed via config update but still broadcasting; miscomputed node IDs after adding a consenter; cross-channel message leakage in multi-channel deployments.

Related errors


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