hyperledger/fabric · error

Failing extracting header during check policy [%s]: [%s]

Error message

Failing extracting header during check policy [%s]: [%s]

What it means

Continuing CheckACL in resourceprovider, after the Proposal unmarshals, its Header must unmarshal via protoutil.UnmarshalHeader. Failure means the embedded Header bytes are not a valid common.Header protobuf, so the policy check aborts with this wrapped error naming the policy and underlying cause.

Source

Thrown at core/aclmgmt/resourceprovider.go:112

// CheckACL implements AClProvider's CheckACL interface so it can be registered
// as a provider with aclmgmt
func (rp *aclmgmtPolicyProviderImpl) CheckACL(polName string, idinfo any) error {
	aclLogger.Debugf("acl check(%s)", polName)

	// we will implement other identifiers. In the end we just need a SignedData
	var sd []*protoutil.SignedData
	switch idinfo := idinfo.(type) {
	case *pb.SignedProposal:
		signedProp := idinfo
		proposal, err := protoutil.UnmarshalProposal(signedProp.ProposalBytes)
		if err != nil {
			return fmt.Errorf("Failing extracting proposal during check policy with policy [%s]: [%s]", polName, err)
		}

		header, err := protoutil.UnmarshalHeader(proposal.Header)
		if err != nil {
			return fmt.Errorf("Failing extracting header during check policy [%s]: [%s]", polName, err)
		}

		shdr, err := protoutil.UnmarshalSignatureHeader(header.SignatureHeader)
		if err != nil {
			return fmt.Errorf("Invalid Proposal's SignatureHeader during check policy [%s]: [%s]", polName, err)
		}

		sd = []*protoutil.SignedData{{
			Data:      signedProp.ProposalBytes,
			Identity:  shdr.Creator,
			Signature: signedProp.Signature,
		}}

	case *common.Envelope:
		var err error
		sd, err = protoutil.EnvelopeAsSignedData(idinfo)
		if err != nil {
			return err

View on GitHub (pinned to 2736b63f8f)

Solutions

  1. Build the proposal with protoutil helpers (CreateProposal/NewProposal) so Header is correctly marshaled, instead of assembling bytes manually.
  2. Check the wrapped error text for the exact protobuf decode failure and fix the offending field.
  3. Ensure the client and peer use compatible fabric-protos versions.
  4. Verify signature integrity: a corrupted header usually also fails signature verification, confirming byte-level corruption upstream.

Example fix

// before
header := &common.Header{...}
proposal.Header = someManualEncoding(header)
// after
hdrBytes, _ := proto.Marshal(header)
proposal.Header = hdrBytes
Defensive patterns

Strategy: validation

Validate before calling

var prop pb.Proposal
if err := proto.Unmarshal(signedProp.ProposalBytes, &prop); err != nil {
    return fmt.Errorf("invalid proposal: %w", err)
}
var hdr common.Header
if err := proto.Unmarshal(prop.Header, &hdr); err != nil {
    return fmt.Errorf("proposal header is not a valid common.Header: %w", err)
}

Type guard

func hasValidHeader(sp *pb.SignedProposal) bool {
    var p pb.Proposal
    if proto.Unmarshal(sp.ProposalBytes, &p) != nil {
        return false
    }
    var h common.Header
    return proto.Unmarshal(p.Header, &h) == nil
}

Try / catch

if err := aclProvider.CheckACL(resName, channelID, signedProp); err != nil {
    if strings.Contains(err.Error(), "Failing extracting header") {
        return fmt.Errorf("proposal header malformed, rebuild with protoutil helpers: %w", err)
    }
    return err
}

Prevention

When it happens

Trigger: A SignedProposal whose inner Proposal contains a Header field that fails protobuf decode — malformed header bytes, header populated with wrong message type, or manual byte assembly errors in custom clients.

Common situations: Hand-rolled fabric clients constructing header bytes by concatenation instead of proto.Marshal; older client protos inconsistent with peer's; payload corruption from custom serialization middleware.

Related errors


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