hyperledger/fabric · error
block data size(%d) is different from Tx filter size(%d)
Error message
block data size(%d) is different from Tx filter size(%d)
What it means
getTxPvtdataInfoFromBlock cross-checks the length of the Tx validation filter bitmap against the number of transactions in block.Data.Data. Each tx in the block must have exactly one validation flag byte; a size mismatch means the block is internally inconsistent and cannot be safely processed, so this error is returned.
Source
Thrown at gossip/privdata/coordinator.go:304
}
}
}
return blockAndPvtData.Block, seqs2Namespaces.asPrivateData(), nil
}
// getTxPvtdataInfoFromBlock parses the block transactions and returns the list of private data items in the block.
// Note that this peer's eligibility for the private data is not checked here.
func (c *coordinator) getTxPvtdataInfoFromBlock(block *common.Block) ([]*ledger.TxPvtdataInfo, error) {
txPvtdataItemsFromBlock := []*ledger.TxPvtdataInfo{}
if block.Metadata == nil || len(block.Metadata.Metadata) <= int(common.BlockMetadataIndex_TRANSACTIONS_FILTER) {
return nil, errors.New("Block.Metadata is nil or Block.Metadata lacks a Tx filter bitmap")
}
txsFilter := txValidationFlags(block.Metadata.Metadata[common.BlockMetadataIndex_TRANSACTIONS_FILTER])
data := block.Data.Data
if len(txsFilter) != len(block.Data.Data) {
return nil, errors.Errorf("block data size(%d) is different from Tx filter size(%d)", len(block.Data.Data), len(txsFilter))
}
for seqInBlock, txEnvBytes := range data {
invalid := txsFilter[seqInBlock] != uint8(peer.TxValidationCode_VALID)
txInfo, err := getTxInfoFromTransactionBytes(txEnvBytes)
if err != nil {
continue
}
colPvtdataInfo := []*ledger.CollectionPvtdataInfo{}
for _, ns := range txInfo.txRWSet.NsRwSets {
for _, hashedCollection := range ns.CollHashedRwSets {
// skip if no writes
if !containsWrites(txInfo.txID, ns.NameSpace, hashedCollection) {
continue
}
cc := privdata.CollectionCriteria{
Channel: txInfo.channelID,View on GitHub (pinned to 2736b63f8f)
Solutions
- Re-obtain the intact block from the orderer or another peer
- Fix the block repair/conversion tooling to keep the Tx filter in sync with block data length
- Rebuild the filter bitmap (one TxValidationCode byte per tx) if you must repair locally
- Correct test fixtures so filter length equals len(block.Data.Data)
Example fix
// before
filter := []byte{0x00} // only 1 flag, but 3 txs
// after
filter := bytes.Repeat([]byte{byte(peer.TxValidationCode_VALID)}, len(block.Data.Data))
block.Metadata.Metadata[common.BlockMetadataIndex_TRANSACTIONS_FILTER] = filter Defensive patterns
Strategy: validation
Validate before calling
filter := block.Metadata.Metadata[common.BlockMetadataIndex_TRANSACTIONS_FILTER]
if len(filter) != len(block.Data.Data) {
return fmt.Errorf("filter size %d != tx count %d", len(filter), len(block.Data.Data))
} Type guard
func txFilterConsistent(b *common.Block) bool {
if b == nil || b.Metadata == nil || b.Data == nil ||
len(b.Metadata.Metadata) <= int(common.BlockMetadataIndex_TRANSACTIONS_FILTER) {
return false
}
return len(b.Metadata.Metadata[common.BlockMetadataIndex_TRANSACTIONS_FILTER]) == len(b.Data.Data)
} Prevention
- When repairing blocks, rebuild the Tx filter to match block data length byte-for-byte
- Verify block integrity (filter length vs tx count) before committing
- Don't modify block.Data.Data in tooling without updating metadata
- Use fabric-native APIs for block export/import instead of manual proto edits
When it happens
Trigger: StoreBlock -> getTxPvtdataInfoFromBlock where len(block.Metadata.Metadata[TRANSACTIONS_FILTER]) != len(block.Data.Data) — e.g. metadata truncated/rebuilt separately from data, or txs added/removed without updating the filter.
Common situations: Ledger repair or export/import tools that rewrote block.Data but not the metadata filter; corrupted block from gossip; custom block builders; tests with mismatched fixture data.
Related errors
- Block.Metadata is nil or Block.Metadata lacks a Tx filter bi
- Block data is empty
- Block header is nil
- message isn't an alive message
- message isn't a stateInfo message
AI-assisted analysis of hyperledger/fabric@2736b63f8f (2026-09-04).
Data as JSON: /api/errors/a11ce07c71504048.
Report an issue: GitHub.