hyperledger/fabric · critical

could not sign the proposal response payload: %v

Error message

could not sign the proposal response payload: %v

What it means

The pluggable endorsement DefaultEndorsement.Endorse signs prpBytes concatenated with the serialized identity using signer.Sign. This error wraps a BCCSP signing failure, meaning no ECDSA signature could be produced for the endorsement.

Source

Thrown at core/handlers/endorsement/plugin/plugin.go:55

// Returns:
// The Endorsement: A signature over the payload, and an identity that is used to verify the signature
// The payload that was given as input (could be modified within this function)
// Or error on failure
func (e *DefaultEndorsement) Endorse(prpBytes []byte, sp *peer.SignedProposal) (*peer.Endorsement, []byte, error) {
	signer, err := e.SigningIdentityForRequest(sp)
	if err != nil {
		return nil, nil, fmt.Errorf("failed fetching signing identity: %v", err)
	}
	// serialize the signing identity
	identityBytes, err := signer.Serialize()
	if err != nil {
		return nil, nil, fmt.Errorf("could not serialize the signing identity: %v", err)
	}

	// sign the concatenation of the proposal response and the serialized endorser identity with this endorser's key
	signature, err := signer.Sign(append(prpBytes, identityBytes...))
	if err != nil {
		return nil, nil, fmt.Errorf("could not sign the proposal response payload: %v", err)
	}
	endorsement := &peer.Endorsement{Signature: signature, Endorser: identityBytes}
	return endorsement, prpBytes, nil
}

// Init injects dependencies into the instance of the Plugin
func (e *DefaultEndorsement) Init(dependencies ...endorsement.Dependency) error {
	for _, dep := range dependencies {
		sIDFetcher, isSigningIdentityFetcher := dep.(identities.SigningIdentityFetcher)
		if !isSigningIdentityFetcher {
			continue
		}
		e.SigningIdentityFetcher = sIDFetcher
		return nil
	}
	return errors.New("could not find SigningIdentityFetcher in dependencies")
}

View on GitHub (pinned to 2736b63f8f)

Solutions

  1. Read the wrapped error to identify keystore vs HSM vs key-format cause
  2. Restore the private key matching the signer certificate in the local MSP keystore with correct permissions
  3. Verify BCCSP configuration (security, pkcs11 library/label/pin) against the deployed HSM
  4. Rebuild/restart the peer or test harness so a fresh signer is obtained

Example fix

// before: HSM pin rotated, sign fails
//   could not sign the proposal response payload: pkcs11: login failed
// after: update BCCSP config and restart
// core.yaml
peer:
  BCCSP:
    PKCS11:
      Pin: <new-pin>
// docker restart peer0.org1.example.com
Defensive patterns

Strategy: try-catch

Validate before calling

// pre-flight: ensure keystore key exists and matches signer cert
if err := verifyKeyCertMatch(mspPath); err != nil {
    return fmt.Errorf("key/cert mismatch, signing will fail: %w", err)
}

Try / catch

sig, err := signer.Sign(append(prpBytes, identityBytes...))
if err != nil {
    logger.Errorf("plugin signing failed (BCCSP/HSM?): %v", err)
    return nil, fmt.Errorf("endorsement aborted: %w", err)
}

Prevention

When it happens

Trigger: Endorse (via EndorseWithPlugin or TestEndorsementPlugin) calls signer.Sign(append(prpBytes, identityBytes...)) and the crypto provider returns an error — private key unavailable, keystore IO error, or HSM failure.

Common situations: Keystore *_sk file missing or unreadable by the plugin host process; PKCS#11 token login failure due to wrong pin/slot in BCCSP config; key object deleted from HSM between fetch and sign in long-running tests.

Related errors


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