hyperledger/fabric · error
message isn't an alive message
Error message
message isn't an alive message
What it means
validateAliveMessage rejects a SignedGossipMessage whose GetAliveMsg() is nil, meaning the envelope's payload decoded to something other than an AliveMessage. The discovery client uses AliveMessages to learn peer membership (endpoint, identity), so it fails the peer. The error is wrapped by the endorser flow as 'failed validating alive message'.
Source
Thrown at discovery/client/client.go:577
}
type endorsementDescriptor struct {
endorsersByGroups map[string][]*Peer
layouts []map[string]int
}
// NewClient creates a new Client instance
func NewClient(createConnection Dialer, s Signer, signerCacheSize uint) *Client {
return &Client{
createConnection: createConnection,
signRequest: NewMemoizeSigner(s, signerCacheSize).Sign,
}
}
func validateAliveMessage(message *gprotoext.SignedGossipMessage) error {
am := message.GetAliveMsg()
if am == nil {
return errors.New("message isn't an alive message")
}
m := am.Membership
if m == nil {
return errors.New("membership is empty")
}
if am.Timestamp == nil {
return errors.New("timestamp is nil")
}
return nil
}
func validateStateInfoMessage(message *gprotoext.SignedGossipMessage) error {
si := message.GetStateInfo()
if si == nil {
return errors.New("message isn't a stateInfo message")
}
if si.Timestamp == nil {
return errors.New("timestamp is nil")View on GitHub (pinned to 2736b63f8f)
Solutions
- Inspect the response: log the SignedGossipMessage type of the offending peer record
- Ensure the discovery target peer is a member of the requested channel and gossip is convergent (peer gossip logs show membership)
- Restart gossip on the target peer so membership/alive messages are regenerated
- Align Fabric versions across peers
- Retry against a different peer
Example fix
// before
peers, err := resp.ForChannel("mychannel") // fails with wrapped validation error
// after
if err != nil {
if strings.Contains(err.Error(), "message isn't an alive message") {
logger.Warnf("discovery peer returned non-alive membership payload; retrying other peer")
}
return nil, err
}
peers, err := resp.ForChannel("mychannel") Defensive patterns
Strategy: validation
Validate before calling
func aliveMsgLooksValid(m *gprotoext.SignedGossipMessage) error {
if m == nil || m.GetAliveMsg() == nil { return errors.New("not an alive message") }
if m.GetAliveMsg().Membership == nil { return errors.New("membership is empty") }
if m.GetAliveMsg().Timestamp == nil { return errors.New("timestamp is nil") }
return nil
} Type guard
func isAliveMsg(m *gprotoext.SignedGossipMessage) bool { return m != nil && m.GetAliveMsg() != nil } Try / catch
if err != nil && strings.Contains(err.Error(), "message isn't an alive message") {
logger.Warnf("discovery peer returned non-membership payload; selecting alternate peer")
return fallbackDiscovery(ctx)
} Prevention
- Ensure gossip is enabled and converged on queried peers
- Keep Fabric versions consistent across the network
- Restart peers whose membership view looks stale
When it happens
Trigger: A discovery response (from peersForChannel or the endorser flow) contains a peer record whose gossip message is a StateInfo, DataMsg, or empty payload instead of an AliveMsg.
Common situations: Peer gossip store corrupted or out of sync; querying a peer before it joined the channel; Fabric version mismatch where membership payloads differ; a peer returning internal state messages instead of membership snapshots.
Related errors
- message isn't a stateInfo message
- group %s isn't mapped to endorsers, but exists in a layout
- failed creating endorser object
- received empty envelope(s) for endorsers for chaincode %s, c
- membership is empty
AI-assisted analysis of hyperledger/fabric@2736b63f8f (2026-09-04).
Data as JSON: /api/errors/003c26f4bc5fa4e9.
Report an issue: GitHub.