hyperledger/fabric · error

nil signer provided

Error message

nil signer provided

What it means

createProposal on ApproverForMyOrg requires a signer (the peer CLI's local MSP identity) to build and sign the proposal. If a.Signer is nil, the command cannot construct a signed transaction, so it returns 'nil signer provided' immediately. This is a client-side precondition check, not a network or peer failure.

Source

Thrown at internal/peer/lifecycle/chaincode/approveformyorg.go:279

		Version:                  chaincodeVersion,
		PackageID:                packageID,
		Sequence:                 int64(sequence),
		EndorsementPlugin:        endorsementPlugin,
		ValidationPlugin:         validationPlugin,
		ValidationParameterBytes: policyBytes,
		InitRequired:             initRequired,
		CollectionConfigPackage:  ccp,
		PeerAddresses:            peerAddresses,
		WaitForEvent:             waitForEvent,
		WaitForEventTimeout:      waitForEventTimeout,
	}

	return input, nil
}

func (a *ApproverForMyOrg) createProposal(inputTxID string) (proposal *pb.Proposal, txID string, err error) {
	if a.Signer == nil {
		return nil, "", errors.New("nil signer provided")
	}

	var ccsrc *lb.ChaincodeSource
	if a.Input.PackageID != "" {
		ccsrc = &lb.ChaincodeSource{
			Type: &lb.ChaincodeSource_LocalPackage{
				LocalPackage: &lb.ChaincodeSource_Local{
					PackageId: a.Input.PackageID,
				},
			},
		}
	} else {
		ccsrc = &lb.ChaincodeSource{
			Type: &lb.ChaincodeSource_Unavailable_{
				Unavailable: &lb.ChaincodeSource_Unavailable{},
			},
		}
	}

View on GitHub (pinned to 2736b63f8f)

Solutions

  1. Set the signing identity env: CORE_PEER_LOCALMSPID and CORE_PEER_MSPCONFIGPATH pointing to an admin user's MSP directory.
  2. When invoking the underlying Go API directly, pass a valid common.Input including PeerAddress and ConnTimeout so InitCallerForMyOrg resolves a Signer before createProposal runs.
  3. Verify FABRIC_CFG_PATH/core.yaml is readable and the MSP directory contains signcerts and keystore files.
  4. Re-run the command with a peer address (-A/--peerAddresses) so the client builds a signer from that peer connection.

Example fix

// before: API call with no signer wired
approver := &chaincode.ApproverForMyOrg{...} // Signer == nil
// after: initialize signer via InitCallerForMyOrg with peer connection info
input := &chaincode.CommonInput{PeerAddress: "peer0.org1:7051", ConnTimeout: 5 * time.Second}
approver, err := chaincode.InitApproverForMyOrg("mychannel", input)
// Signer is now populated from local MSP
Defensive patterns

Strategy: validation

Validate before calling

// before invoking approve, ensure a signing identity is configured
if os.Getenv("CORE_PEER_MSPCONFIGPATH") == "" || os.Getenv("CORE_PEER_LOCALMSPID") == "" {
    return errors.New("signing identity not configured: set CORE_PEER_MSPCONFIGPATH and CORE_PEER_LOCALMSPID")
}
if _, err := os.Stat(os.Getenv("CORE_PEER_MSPCONFIGPATH") + "/signcerts"); err != nil {
    return fmt.Errorf("invalid MSP dir: %w", err)
}

Type guard

// in Go, guard before building the proposal
func hasSigner(a *chaincode.ApproverForMyOrg) bool {
    return a != nil && a.Signer != nil
}

Try / catch

_, err := approver.Approve(proposal)
if err != nil && strings.Contains(err.Error(), "nil signer") {
    return fmt.Errorf("configure signing identity (CORE_PEER_MSPCONFIGPATH / peer address): %w", err)
}

Prevention

When it happens

Trigger: Calling approveformyorg (or invoking createProposal directly in Go code) without specifying -o orderer/peer connection info that yields a signing identity — i.e. no --peerAddress/--tlsRootCertFile + MSP context, or constructing ApproverForMyOrg with Signer unset when the common.Input lacks the signing identity parameters.

Common situations: Forgetting --peerAddress / --connTimeout or running outside an admin CLI context where the local MSP path (FABRIC_CFG_PATH, CORE_PEER_LOCALMSPID, CORE_PEER_MSPCONFIGPATH) is not configured, so no signer can be loaded.

Related errors


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