Server
This section contains the details on how to use Garuda for our games in phoenix.
Adding GameManager
GameManager is the root supervisor for all the systems mentioned below.
Basically we have to add this supervisor module to the application.ex
of
a Phoenix project as a child inside the start function.
Add like below, if we dont want to pass extra options.
Garuda.GameManager
or, we have to add GameManager like,
{Garuda.GameManager, max_sup: 10}
For more details, go through GameManager module.
Matchmaking system
Matchmaking system is inbuilt into the core, so developers doesn't have to know any api to work with it. For every room created, Garuda will create a unique matchId for it. If we have to use custom matchId, then we can specify it from client side.
Framework system
Framework has 3 parts
- GameSocket - Extends Phoenix.Socket with extra game behaviours.
- GameChannel - Extends Phoenix.Channel with extra game behaviours.
- GameRoom - Extends GenServer with extra game behaviours.
GameSocket
In user_socket.ex
, we can do
defmodule TictactoePhxWeb.UserSocket do
use Garuda.GameSocket
game_channel "tictactoe", TictactoePhxWeb.TictactoeChannel, TictactoePhx.TictactoeRoom
end
Here we replaced use Phoenix.Socket
with use Garuda.GameSocket
. Also we have to
remove the connect/3
, which we normally use in user_socket.ex
, GameSocket module will take care of that.
On the third line of above code snippet, we are mapping our socket events. We are specifying the name of our game, the GameChannel (where we handle the events), and the GameRoom where the core gameplay logic should happen. For more details, go through GameSocket module.
GameChannel
defmodule TictactoePhxWeb.TictactoeChannel do
use Garuda.GameChannel
@impl true
def on_join(_params, _socket) do
IO.puts("Player Joined")
end
@impl true
def on_rejoin(_params, _socket) do
IO.puts("Player rejoined")
end
@impl true
def authorized?(_params) do
# Custom authorization code
true
end
@impl true
def handle_in("player_move", cell, socket) do
# Handling usual events from client
{:noreply, socket}
end
end
Here we replaced use Phoenix.Channel
with use Garuda.GameChannel
.
GameChannel works exactly like Phoenix Channel. We don't have to use join/3
.
Instead there are 3 mandatory callbacks, on_join/2
(calls when player is authenticated and joins the channel), authorized?/1
(custom authorization), on_rejoin/2
(when player rejoins the game, after a short delay).
We can use all the other callbacks in phoenix channels, here too. Like handle_in/3
, handle_out/3
etc.
For more details, go through GameChannel module.
GameRoom
defmodule TictactoePhx.TictactoeRoom do
use Garuda.GameRoom, expiry: 120_000
def create(_opts) do
# Return the initial game state.
gamestate
end
def leave(player_id, game_state) do
# handle player leaving.
{:ok, gamestate}
end
end
GameRooms are extended genservers, where our core gameplay logic resides.
We don't have to use Genserver functions like start_link/3
or init/2
.
init/2
is replaced by create/1
. Rest everything works like genserver.
For more detauls, go through GameRoom
Monitoring system
Real-time monitoring of game-server is first-class in Garuda. Configuring monitoring is covered here, Realtime-monitoring