diff options
author | Santo Cariotti <santo@dcariotti.me> | 2025-04-18 16:09:32 +0200 |
---|---|---|
committer | Santo Cariotti <santo@dcariotti.me> | 2025-04-18 16:09:32 +0200 |
commit | 7c5a6176b27b6b0c0c3ef8a4aedbdec871391a80 (patch) | |
tree | 5ebfc9b402b8aa941ab9617b5f3842071edafedf | |
parent | 0b4fb251efdfd2fba7cd6154f5f59bd61ede15f1 (diff) |
Add type on messages between peers
-rw-r--r-- | pkg/p2p/network.go | 4 | ||||
-rw-r--r-- | pkg/p2p/network_test.go | 6 | ||||
-rw-r--r-- | pkg/ui/multiplayer/multiplayer.go | 20 | ||||
-rw-r--r-- | pkg/ui/views/game.go | 6 | ||||
-rw-r--r-- | pkg/ui/views/game_keymap.go | 2 | ||||
-rw-r--r-- | pkg/ui/views/game_moves.go | 12 |
6 files changed, 34 insertions, 16 deletions
diff --git a/pkg/p2p/network.go b/pkg/p2p/network.go index 0acbdfa..13c99b0 100644 --- a/pkg/p2p/network.go +++ b/pkg/p2p/network.go @@ -14,6 +14,7 @@ import ( // `Message` represents a structured message on this network. type Message struct { + Type []byte `json:"type"` Timestamp int64 `json:"timestamp"` Source NetworkID `json:"source"` Payload []byte `json:"payload"` @@ -107,7 +108,7 @@ func (n *TCPNetwork) AddPeer(remoteID NetworkID, addr string) { } // Send methods is used to send a message to a specified remote peer -func (n *TCPNetwork) Send(remoteID NetworkID, payload []byte) error { +func (n *TCPNetwork) Send(remoteID NetworkID, messageType []byte, payload []byte) error { n.Lock() peerConn, exists := n.connections[remoteID] n.Unlock() @@ -123,6 +124,7 @@ func (n *TCPNetwork) Send(remoteID NetworkID, payload []byte) error { } message := Message{ + Type: messageType, Payload: payload, Source: n.id, Timestamp: time.Now().Unix(), diff --git a/pkg/p2p/network_test.go b/pkg/p2p/network_test.go index fd5dde0..15d0d8e 100644 --- a/pkg/p2p/network_test.go +++ b/pkg/p2p/network_test.go @@ -44,10 +44,10 @@ func TestPeerToPeerCommunication(t *testing.T) { time.Sleep(5 * time.Second) // Send a message from peer-1 to peer-2 - err := peer1.Send("peer-2", []byte("Hey from peer-1!")) + err := peer1.Send("peer-2", []byte("simple-msg"), []byte("Hey from peer-1!")) assert.NoError(t, err) - err = peer2.Send("peer-1", []byte("Hey from peer-2!")) + err = peer2.Send("peer-1", []byte("simple-msg"), []byte("Hey from peer-2!")) assert.NoError(t, err) // Allow some time for the message to be received and handled @@ -74,6 +74,6 @@ func TestSendFailure(t *testing.T) { _ = NewTCPNetwork("peer-2", peer2Opts) // Attempt to send a message without establishing a connection first - err := peer1.Send("peer-2", []byte("Message without connection")) + err := peer1.Send("peer-2", []byte("msg"), []byte("Message without connection")) assert.Error(t, err, "Expected error when sending to a non-connected peer") } diff --git a/pkg/ui/multiplayer/multiplayer.go b/pkg/ui/multiplayer/multiplayer.go index ac3bc7a..98ccfb4 100644 --- a/pkg/ui/multiplayer/multiplayer.go +++ b/pkg/ui/multiplayer/multiplayer.go @@ -8,6 +8,18 @@ import ( "go.uber.org/zap" ) +type MoveType string + +const ( + AbandonGameMessage MoveType = "abandon" + MoveGameMessage MoveType = "new-move" +) + +type GameMove struct { + Type []byte `json:"type"` + Payload []byte `json:"payload"` +} + type GameNetwork struct { server *p2p.TCPNetwork me p2p.NetworkID @@ -37,8 +49,8 @@ func (n *GameNetwork) Me() p2p.NetworkID { return n.me } -func (n *GameNetwork) Send(payload []byte) error { - return n.server.Send(n.peer, payload) +func (n *GameNetwork) Send(messageType []byte, payload []byte) error { + return n.server.Send(n.peer, messageType, payload) } func (n *GameNetwork) AddPeer(remoteID p2p.NetworkID, addr string) { @@ -55,9 +67,9 @@ func (n *GameNetwork) Close() error { logger, _ := logger.GetLogger() if err != nil { - logger.Sugar().Errorf("Can't close connection for network '%+v': %s", n, err.Error()) + logger.Sugar().Errorf("can't close connection for network '%+v': %s", n, err.Error()) } else { - logger.Sugar().Infof("Connection closed for network '%+v'", n) + logger.Sugar().Infof("connection closed for network '%+v'", n) } return err diff --git a/pkg/ui/views/game.go b/pkg/ui/views/game.go index 4e8cc87..3742101 100644 --- a/pkg/ui/views/game.go +++ b/pkg/ui/views/game.go @@ -28,7 +28,7 @@ type GameModel struct { game *database.Game network *multiplayer.GameNetwork chessGame *chess.Game - incomingMoves chan string + incomingMoves chan multiplayer.GameMove turn int availableMovesList list.Model } @@ -56,7 +56,7 @@ func NewGameModel(width, height int, currentGameID int, network *multiplayer.Gam currentGameID: currentGameID, network: network, chessGame: chess.NewGame(chess.UseNotation(chess.UCINotation{})), - incomingMoves: make(chan string), + incomingMoves: make(chan multiplayer.GameMove), turn: 0, availableMovesList: moveList, } @@ -122,7 +122,7 @@ func (m GameModel) Update(msg tea.Msg) (tea.Model, tea.Cmd) { m.err = err } else { m.turn++ - m.network.Send([]byte(moveStr)) + m.network.Send([]byte("new-move"), []byte(moveStr)) m.err = nil } cmds = append(cmds, m.getMoves(), m.updateMovesListCmd()) diff --git a/pkg/ui/views/game_keymap.go b/pkg/ui/views/game_keymap.go index 00b062f..283a69c 100644 --- a/pkg/ui/views/game_keymap.go +++ b/pkg/ui/views/game_keymap.go @@ -44,7 +44,7 @@ func (m GameModel) handleKeyMsg(msg tea.KeyMsg) (GameModel, tea.Cmd) { outcome = string(chess.WhiteWon) } - m.network.Send([]byte("🏳️")) + m.network.Send([]byte("abandon"), []byte("🏳️")) return m, m.endGame(outcome) } case key.Matches(msg, m.keys.Quit): diff --git a/pkg/ui/views/game_moves.go b/pkg/ui/views/game_moves.go index daf24e6..ea1fa02 100644 --- a/pkg/ui/views/game_moves.go +++ b/pkg/ui/views/game_moves.go @@ -4,6 +4,7 @@ import ( "fmt" "github.com/boozec/rahanna/pkg/p2p" + "github.com/boozec/rahanna/pkg/ui/multiplayer" "github.com/charmbracelet/bubbles/list" tea "github.com/charmbracelet/bubbletea" "github.com/notnil/chess" @@ -25,16 +26,19 @@ func (i item) FilterValue() string { return i.title } func (m *GameModel) getMoves() tea.Cmd { m.network.AddReceiveFunction(func(msg p2p.Message) { - payload := string(msg.Payload) - m.incomingMoves <- payload + gm := multiplayer.GameMove{ + Type: msg.Type, + Payload: msg.Payload, + } + m.incomingMoves <- gm }) return func() tea.Msg { move := <-m.incomingMoves - if move == "🏳️" { + if multiplayer.MoveType(string(move.Type)) == multiplayer.AbandonGameMessage { return EndGameMsg{abandoned: true} } - return ChessMoveMsg(move) + return ChessMoveMsg(string(move.Payload)) } } |