github.com/osdi23p228/fabric@v0.0.0-20221218062954-77808885f5db/orderer/consensus/consensus.go (about)

     1  /*
     2  Copyright IBM Corp. 2017 All Rights Reserved.
     3  
     4  SPDX-License-Identifier: Apache-2.0
     5  */
     6  
     7  package consensus
     8  
     9  import (
    10  	cb "github.com/hyperledger/fabric-protos-go/common"
    11  	"github.com/osdi23p228/fabric/common/channelconfig"
    12  	"github.com/osdi23p228/fabric/internal/pkg/identity"
    13  	"github.com/osdi23p228/fabric/orderer/common/blockcutter"
    14  	"github.com/osdi23p228/fabric/orderer/common/msgprocessor"
    15  	"github.com/osdi23p228/fabric/protoutil"
    16  )
    17  
    18  // Consenter defines the backing ordering mechanism.
    19  type Consenter interface {
    20  	// HandleChain should create and return a reference to a Chain for the given set of resources.
    21  	// It will only be invoked for a given chain once per process.  In general, errors will be treated
    22  	// as irrecoverable and cause system shutdown.  See the description of Chain for more details
    23  	// The second argument to HandleChain is a pointer to the metadata stored on the `ORDERER` slot of
    24  	// the last block committed to the ledger of this Chain. For a new chain, or one which is migrated,
    25  	// this metadata will be nil (or contain a zero-length Value), as there is no prior metadata to report.
    26  	HandleChain(support ConsenterSupport, metadata *cb.Metadata) (Chain, error)
    27  
    28  	// JoinChain should create and return a reference to a Chain when the channel is started with a join-block
    29  	// that is not a genesis block (i.e. join-block.number>0), and a ledger with height <= than join-block.number.
    30  	// This means that there is a gap between the join-block and the last block in the ledger that requires
    31  	// on-boarding. In contrast, HandleChain creates a Chain based on the last block found in the ledger.
    32  	JoinChain(support ConsenterSupport, joinBlock *cb.Block) (Chain, error)
    33  }
    34  
    35  // MetadataValidator performs the validation of updates to ConsensusMetadata during config updates to the channel.
    36  // NOTE: We expect the MetadataValidator interface to be optionally implemented by the Consenter implementation.
    37  //       If a Consenter does not implement MetadataValidator, we default to using a no-op MetadataValidator.
    38  type MetadataValidator interface {
    39  	// ValidateConsensusMetadata determines the validity of a ConsensusMetadata update during config
    40  	// updates on the channel.
    41  	// Since the ConsensusMetadata is specific to the consensus implementation (independent of the particular
    42  	// chain) this validation also needs to be implemented by the specific consensus implementation.
    43  	ValidateConsensusMetadata(oldOrdererConfig, newOrdererConfig channelconfig.Orderer, newChannel bool) error
    44  }
    45  
    46  // Chain defines a way to inject messages for ordering.
    47  // Note, that in order to allow flexibility in the implementation, it is the responsibility of the implementer
    48  // to take the ordered messages, send them through the blockcutter.Receiver supplied via HandleChain to cut blocks,
    49  // and ultimately write the ledger also supplied via HandleChain.  This design allows for two primary flows
    50  // 1. Messages are ordered into a stream, the stream is cut into blocks, the blocks are committed (solo, kafka)
    51  // 2. Messages are cut into blocks, the blocks are ordered, then the blocks are committed (sbft)
    52  type Chain interface {
    53  	// Order accepts a message which has been processed at a given configSeq.
    54  	// If the configSeq advances, it is the responsibility of the consenter
    55  	// to revalidate and potentially discard the message
    56  	// The consenter may return an error, indicating the message was not accepted
    57  	Order(env *cb.Envelope, configSeq uint64) error
    58  
    59  	// Configure accepts a message which reconfigures the channel and will
    60  	// trigger an update to the configSeq if committed.  The configuration must have
    61  	// been triggered by a ConfigUpdate message. If the config sequence advances,
    62  	// it is the responsibility of the consenter to recompute the resulting config,
    63  	// discarding the message if the reconfiguration is no longer valid.
    64  	// The consenter may return an error, indicating the message was not accepted
    65  	Configure(config *cb.Envelope, configSeq uint64) error
    66  
    67  	// WaitReady blocks waiting for consenter to be ready for accepting new messages.
    68  	// This is useful when consenter needs to temporarily block ingress messages so
    69  	// that in-flight messages can be consumed. It could return error if consenter is
    70  	// in erroneous states. If this blocking behavior is not desired, consenter could
    71  	// simply return nil.
    72  	WaitReady() error
    73  
    74  	// Errored returns a channel which will close when an error has occurred.
    75  	// This is especially useful for the Deliver client, who must terminate waiting
    76  	// clients when the consenter is not up to date.
    77  	Errored() <-chan struct{}
    78  
    79  	// Start should allocate whatever resources are needed for staying up to date with the chain.
    80  	// Typically, this involves creating a thread which reads from the ordering source, passes those
    81  	// messages to a block cutter, and writes the resulting blocks to the ledger.
    82  	Start()
    83  
    84  	// Halt frees the resources which were allocated for this Chain.
    85  	Halt()
    86  }
    87  
    88  //go:generate counterfeiter -o mocks/mock_consenter_support.go . ConsenterSupport
    89  
    90  // ConsenterSupport provides the resources available to a Consenter implementation.
    91  type ConsenterSupport interface {
    92  	identity.SignerSerializer
    93  	msgprocessor.Processor
    94  
    95  	// VerifyBlockSignature verifies a signature of a block with a given optional
    96  	// configuration (can be nil).
    97  	VerifyBlockSignature([]*protoutil.SignedData, *cb.ConfigEnvelope) error
    98  
    99  	// BlockCutter returns the block cutting helper for this channel.
   100  	BlockCutter() blockcutter.Receiver
   101  
   102  	// SharedConfig provides the shared config from the channel's current config block.
   103  	SharedConfig() channelconfig.Orderer
   104  
   105  	// ChannelConfig provides the channel config from the channel's current config block.
   106  	ChannelConfig() channelconfig.Channel
   107  
   108  	// CreateNextBlock takes a list of messages and creates the next block based on the block with highest block number committed to the ledger
   109  	// Note that either WriteBlock or WriteConfigBlock must be called before invoking this method a second time.
   110  	CreateNextBlock(messages []*cb.Envelope) *cb.Block
   111  
   112  	// Block returns a block with the given number,
   113  	// or nil if such a block doesn't exist.
   114  	Block(number uint64) *cb.Block
   115  
   116  	// WriteBlock commits a block to the ledger.
   117  	WriteBlock(block *cb.Block, encodedMetadataValue []byte)
   118  
   119  	// WriteConfigBlock commits a block to the ledger, and applies the config update inside.
   120  	WriteConfigBlock(block *cb.Block, encodedMetadataValue []byte)
   121  
   122  	// Sequence returns the current config sequence.
   123  	Sequence() uint64
   124  
   125  	// ChannelID returns the channel ID this support is associated with.
   126  	ChannelID() string
   127  
   128  	// Height returns the number of blocks in the chain this channel is associated with.
   129  	Height() uint64
   130  
   131  	// Append appends a new block to the ledger in its raw form,
   132  	// unlike WriteBlock that also mutates its metadata.
   133  	Append(block *cb.Block) error
   134  }
   135  
   136  // NoOpMetadataValidator implements a MetadataValidator that always returns nil error irrespecttive of the inputs.
   137  type NoOpMetadataValidator struct {
   138  }
   139  
   140  // ValidateConsensusMetadata determines the validity of a ConsensusMetadata update during config updates
   141  // on the channel, and it always returns nil error for the NoOpMetadataValidator implementation.
   142  func (n NoOpMetadataValidator) ValidateConsensusMetadata(oldChannelConfig, newChannelConfig channelconfig.Orderer, newChannel bool) error {
   143  	return nil
   144  }