Begin implementing logging player into a game
All checks were successful
Build & Test / nix-build (push) Successful in 1m9s

This commit is contained in:
Kodi Craft 2024-08-18 13:44:09 +02:00
parent 11db275db2
commit 78442a94af
Signed by: kodi
GPG Key ID: 69D9EED60B242822
6 changed files with 85 additions and 17 deletions

View File

@ -1,9 +1,26 @@
# Amethyst - An experimental Minecraft server written in Elixir.
# Copyright (C) 2024 KodiCraft
#
# This program is free software: you can redistribute it and/or modify
# it under the terms of the GNU Affero General Public License as
# published by the Free Software Foundation, either version 3 of the
# License, or (at your option) any later version.
#
# This program is distributed in the hope that it will be useful,
# but WITHOUT ANY WARRANTY; without even the implied warranty of
# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
# GNU Affero General Public License for more details.
#
# You should have received a copy of the GNU Affero General Public License
# along with this program. If not, see <https://www.gnu.org/licenses/>.
defmodule Amethyst.API.Game do defmodule Amethyst.API.Game do
@moduledoc """ @moduledoc """
This module includes the interface for defining and registering This module includes the interface for defining and registering
a game with Amethyst. a game with Amethyst.
""" """
@callback instantiate() :: {:ok, new_state :: term} | {:error, reason :: term} @callback instantiate() :: {:ok, new_state :: term} | {:error, reason :: term}
@callback login(connection_process :: pid(), player_cfg :: keyword(), state :: term) :: {:ok, new_state :: term} | {:refuse, new_state :: term}
defmacro __using__(opts) do defmacro __using__(opts) do
meta = Keyword.get(opts, :meta, []) meta = Keyword.get(opts, :meta, [])
@ -23,8 +40,26 @@ defmodule Amethyst.API.Game do
loop(state) loop(state)
end end
defp loop(state) do defp loop(state) do
loop(state) receive do
{:login, caller, cfg} ->
case login(caller, cfg, state) do
{:ok, state} ->
send(caller, :ok)
loop(state)
{:refuse, state} ->
send(caller, :refuse)
loop(state)
end
end
end end
end end
end end
def login(pid, cfg) do
send(pid, {:login, self(), cfg})
receive do
:ok -> :ok
:refuse -> :refuse
end
end
end end

View File

@ -1,3 +1,19 @@
# Amethyst - An experimental Minecraft server written in Elixir.
# Copyright (C) 2024 KodiCraft
#
# This program is free software: you can redistribute it and/or modify
# it under the terms of the GNU Affero General Public License as
# published by the Free Software Foundation, either version 3 of the
# License, or (at your option) any later version.
#
# This program is distributed in the hope that it will be useful,
# but WITHOUT ANY WARRANTY; without even the implied warranty of
# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
# GNU Affero General Public License for more details.
#
# You should have received a copy of the GNU Affero General Public License
# along with this program. If not, see <https://www.gnu.org/licenses/>.
defmodule Amethyst.GameCoordinator do defmodule Amethyst.GameCoordinator do
use GenServer use GenServer
@ -55,13 +71,13 @@ defmodule Amethyst.GameCoordinator do
end end
end end
def create(type) do def create(type) when is_atom(type) do
GenServer.call({:global, __MODULE__}, {:create, type}) GenServer.call({:global, __MODULE__}, {:create, type})
end end
def find(type) do def find(type) when is_atom(type) do
GenServer.call({:global, __MODULE__}, {:find, type}) GenServer.call({:global, __MODULE__}, {:find, type})
end end
def find_or_create(type) do def find_or_create(type) when is_atom(type) do
GenServer.call({:global, __MODULE__}, {:find_or_create, type}) GenServer.call({:global, __MODULE__}, {:find_or_create, type})
end end
end end

View File

@ -1,3 +1,19 @@
# Amethyst - An experimental Minecraft server written in Elixir.
# Copyright (C) 2024 KodiCraft
#
# This program is free software: you can redistribute it and/or modify
# it under the terms of the GNU Affero General Public License as
# published by the Free Software Foundation, either version 3 of the
# License, or (at your option) any later version.
#
# This program is distributed in the hope that it will be useful,
# but WITHOUT ANY WARRANTY; without even the implied warranty of
# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
# GNU Affero General Public License for more details.
#
# You should have received a copy of the GNU Affero General Public License
# along with this program. If not, see <https://www.gnu.org/licenses/>.
defmodule Amethyst.GameRegistry do defmodule Amethyst.GameRegistry do
use GenServer use GenServer

View File

@ -327,16 +327,14 @@ defmodule Amethyst.Server.Configuration do
end end
# Acknowledge Finish Configuration https://wiki.vg/Protocol#Acknowledge_Finish_Configuration # Acknowledge Finish Configuration https://wiki.vg/Protocol#Acknowledge_Finish_Configuration
def handle({:acknowledge_finish_configuration}, client, state) do def handle({:acknowledge_finish_configuration}, client, state) do
game = Amethyst.GameRegistry.get_default() |> elem(0) |> Amethyst.GameCoordinator.find_or_create()
state = Keyword.put(state, :game, game)
Amethyst.API.Game.login(game, state)
# TODO: All of this stuff should obviously not be hardcoded here # TODO: All of this stuff should obviously not be hardcoded here
Amethyst.Server.Play.transmit({:login, Amethyst.Server.Play.transmit({:login,
0, false, ["minecraft:overworld"], 0, 16, 16, false, true, true, 0, 0, false, ["minecraft:overworld"], 0, 16, 16, false, true, true, 0,
"minecraft:overworld", <<0::64>>, :spectator, nil, false, true, nil, 0, false "minecraft:overworld", <<0::64>>, :spectator, nil, false, true, nil, 0, false
}, client) }, client)
game = Amethyst.GameRegistry.get_default()
if game == nil do
raise RuntimeError, "No game is set as a default! A single game must be defined as default for players to be able to join."
end
state = Keyword.put(state, :game, game)
Amethyst.Server.Play.serve(client, state) Amethyst.Server.Play.serve(client, state)
end end
# Serverbound Plugin Message https://wiki.vg/Protocol#Serverbound_Plugin_Message_(configuration) # Serverbound Plugin Message https://wiki.vg/Protocol#Serverbound_Plugin_Message_(configuration)

View File

@ -1,8 +1,15 @@
defmodule Example.Game do defmodule Example.Game do
require Logger
use Amethyst.API.Game, meta: [default: true] use Amethyst.API.Game, meta: [default: true]
@impl true @impl true
def instantiate() do def instantiate() do
{:ok, [:hello]} {:ok, [:hello]}
end end
@impl true
def login(from, cfg, state) do
Logger.debug("Player logged in from #{inspect(from)}: #{inspect(cfg)}")
{:ok, state}
end
end end

View File

@ -8,11 +8,7 @@
# configurations or dependencies per app, it is best to # configurations or dependencies per app, it is best to
# move said applications out of the umbrella. # move said applications out of the umbrella.
import Config import Config
config :logger, :console,
# Sample configuration: level: :debug,
# format: "$date $time [$level] $metadata$message",
# config :logger, :console, metadata: []
# level: :info,
# format: "$date $time [$level] $metadata$message\n",
# metadata: [:user_id]
#