hyperledger/fabric · error

invalid validation chain. Parent certificate should be a lea

Error message

invalid validation chain. Parent certificate should be a leaf of the certification tree [%v]

What it means

After validating the chain, getValidationChain checks that the parent certificate (chain[1], or chain[0] for intermediate chains) is a leaf of the certification tree, using certificationTreeInternalNodesMap populated at setup. If the parent is an internal (intermediate) node that is not properly registered as a certification-tree leaf parent, the chain layout doesn't match the MSP's configured CA hierarchy and validation is rejected.

Source

Thrown at msp/mspimpl.go:862

func (msp *bccspmsp) getValidationChain(cert *x509.Certificate, isIntermediateChain bool) ([]*x509.Certificate, error) {
	validationChain, err := msp.getUniqueValidationChain(cert, msp.getValidityOptsForCert(cert))
	if err != nil {
		return nil, errors.WithMessage(err, "failed getting validation chain")
	}

	// we expect a chain of length at least 2
	if len(validationChain) < 2 {
		return nil, errors.Errorf("expected a chain of length at least 2, got %d", len(validationChain))
	}

	// check that the parent is a leaf of the certification tree
	// if validating an intermediate chain, the first certificate will the parent
	parentPosition := 1
	if isIntermediateChain {
		parentPosition = 0
	}
	if msp.certificationTreeInternalNodesMap[string(validationChain[parentPosition].Raw)] {
		return nil, errors.Errorf("invalid validation chain. Parent certificate should be a leaf of the certification tree [%v]", cert.Raw)
	}
	return validationChain, nil
}

// getCertificationChainIdentifier returns the certification chain identifier of the passed identity within this msp.
// The identifier is computes as the SHA256 of the concatenation of the certificates in the chain.
func (msp *bccspmsp) getCertificationChainIdentifier(id Identity) ([]byte, error) {
	chain, err := msp.getCertificationChain(id)
	if err != nil {
		return nil, errors.WithMessagef(err, "failed getting certification chain for [%v]", id)
	}

	// chain[0] is the certificate representing the identity.
	// It will be discarded
	return msp.getCertificationChainIdentifierFromChain(chain[1:])
}

func (msp *bccspmsp) getCertificationChainIdentifierFromChain(chain []*x509.Certificate) ([]byte, error) {

View on GitHub (pinned to 2736b63f8f)

Solutions

  1. Put only true root CAs in cacerts and intermediate CAs in intermediatescerts so the parent of any chain is a leaf of the certification tree
  2. Update the channel/local MSP configuration to match the actual issuing CA hierarchy
  3. Re-issue identities from the CA whose chain layout matches the MSP configuration
  4. Regenerate the MSP directory with cryptogen/fabric-ca after hierarchy changes

Example fix

// before
// cacerts: [intermediateCA.pem]
// after
// cacerts: [rootCA.pem], intermediatescerts: [intermediateCA.pem]
Defensive patterns

Strategy: validation

Validate before calling

// ensure parent of identity is a leaf CA in your hierarchy
if cert.Issuer.Equal(intermediateCA.Subject) {
	// intermediateCA must be in intermediatescerts, root in cacerts
}

Try / catch

chain, err := msp.GetCertificationChain(id)
if err != nil && strings.Contains(err.Error(), "Parent certificate should be a leaf") {
	// re-check MSP CA hierarchy configuration
}

Prevention

When it happens

Trigger: getCertificationChainForBCCSPIdentity or getCertifiersIdentifier validates an identity whose direct parent certificate's raw DER is present in certificationTreeInternalNodesMap — i.e. the immediate parent is an intermediate CA that the MSP recorded as an internal node rather than an acceptable chain parent, e.g. an identity issued directly by an intermediate that was configured as a root.

Common situations: MSP config lists an intermediate CA in cacerts so identities signed by it produce parents that map to internal nodes; mixing intermediatescerts/cacerts contents after migrating from an old org MSP; channel MSP differing from local MSP CA hierarchy.

Understand the failure class

Related errors


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