package consensus

import "time"

// MessageType representa o tipo de mensagem de consenso.
type MessageType string

const (
	ProposalType   MessageType = "PROPOSAL"
	PrevoteType    MessageType = "PREVOTE"
	PrecommitType  MessageType = "PRECOMMIT"
)

// ConsensusMessage representa uma mensagem genérica de consenso.
type ConsensusMessage interface {
	Type() MessageType
	Height() uint64
	Round() uint64
	ValidatorID() string
	Timestamp() time.Time
}

// BaseMsg contém os campos comuns entre as mensagens.
type BaseMsg struct {
	MsgType     MessageType
	HeightVal   uint64
	RoundVal    uint64
	Validator   string
	Time        time.Time
}

func (b BaseMsg) Type() MessageType     { return b.MsgType }
func (b BaseMsg) Height() uint64        { return b.HeightVal }
func (b BaseMsg) Round() uint64         { return b.RoundVal }
func (b BaseMsg) ValidatorID() string   { return b.Validator }
func (b BaseMsg) Timestamp() time.Time  { return b.Time }

// ProposalMsg carrega a proposta de bloco feita por um validador.
type ProposalMsg struct {
	BaseMsg
	BlockHash string // Hash do bloco proposto
}

// PrevoteMsg representa um voto inicial a favor de um bloco ou nil.
type PrevoteMsg struct {
	BaseMsg
	BlockHash string // Pode ser "" para nil
}

// PrecommitMsg representa o voto firme para travar o bloco.
type PrecommitMsg struct {
	BaseMsg
	BlockHash string // Pode ser "" para nil
}