Playfab、Photonfusionを全く知らないおっさん49歳がだいたい1ヶ月ぐらいで、遠回りしまくってみた内容をまとめてみました。
主な役割を担うおっさん達
Server
Agent
Heartbeat
Build
Client
5つのおっさんが必要
ローカルでの開発に必要なおっさん達
Docker Desktop
LocalMpsAgent
おっさん達の詳細
- Server
- Playfab Multiplayer Playfab内で、複数人数用のサーバーのサービスを用意してくれるおっさん
- Agent
- 「Playfab Multiplayerおっさん」を呼び出すためのおっさん
- Heartbeat
- 「Serverのおっさん」と、「Agentのおっさん」との間で、生きてますかぁ?生きてますよぉの生存確認を伝えるおっさん
- Build
- 画面は持たずClientのリクエストに応じて返事をするおっさん Unity で書いたServerの役割を持つ部分 FuisonのRunnerのインスタンを持ち回し、StartSimulationで、環境を作る
- Client
- エンドユーザーの端末に入りユーザーからのボタンや十字キーからの命令を一旦受け取ったり、画面を生成するおっさん
下記が実際のコードUnityで適当にobjectを作りスクリプトを当てれば大丈夫
namespace Fusion.Sample.DedicatedServer
{
using System.Collections.Generic;
using UnityEngine;
using UnityEngine.SceneManagement;
using PlayFab;
using Fusion.Photon.Realtime;
using Fusion.Sockets;
using System.Collections;
using System.Threading.Tasks;
using System.Net;
public class ServerManager : MonoBehaviour
{
[SerializeField] private NetworkRunner _runnerPrefab;
public bool Debugging = true;
public void Awake()
{
Debug.Log("ServerManager Awake");
if (CommandLineUtils.IsHeadlessMode() == false) {
SceneManager.LoadScene((int)SceneDefs.CLIENTMENU, LoadSceneMode.Single);
return;
}
}
void Start () {
Debug.Log("ServerManager Start");
PlayFabMultiplayerAgentAPI.Start();
PlayFabMultiplayerAgentAPI.IsDebugging = Debugging;
PlayFabMultiplayerAgentAPI.OnServerActiveCallback += OnServerActive;
StartCoroutine(ReadyForPlayers());
}
IEnumerator ReadyForPlayers()
{
Debug.Log("ServerManager ReadyForPlayers");
yield return new WaitForSeconds(.5f);
PlayFabMultiplayerAgentAPI.ReadyForPlayers();
}
private void OnServerActive()
{
Debug.Log("ServerManager OnServerActive");
//For Fusion
StartFusion();
}
async void StartFusion() {
Debug.Log("ServerManager StartFusion");
Application.targetFrameRate = 30;
var config = DedicatedServerConfig.Resolve();
Debug.Log(config);
var runner = Instantiate(_runnerPrefab);
var result = await StartSimulation(
runner,
config.SessionName,
config.SessionProperties,
config.Port,
config.Lobby,
config.Region,
config.PublicIP,
config.PublicPort
);
if (result.Ok) {
Log.Debug($"Runner Start DONE");
} else {
Log.Debug($"Error while starting Server: {result.ShutdownReason}");
Application.Quit(1);
}
}
private Task<StartGameResult> StartSimulation(
NetworkRunner runner,
string SessionName,
Dictionary<string, SessionProperty> customProps,
ushort port,
string customLobby,
string customRegion,
string customPublicIP = null,
ushort customPublicPort = 0
) {
Debug.Log("StartFusion StartSimulation");
// Build Custom Photon Config
var photonSettings = PhotonAppSettings.Instance.AppSettings.GetCopy();
if (string.IsNullOrEmpty(customRegion) == false) {
photonSettings.FixedRegion = customRegion.ToLower();
}
// Build Custom External Addr
NetAddress? externalAddr = null;
if (string.IsNullOrEmpty(customPublicIP) == false && customPublicPort > 0) {
if (IPAddress.TryParse(customPublicIP, out var _)) {
externalAddr = NetAddress.CreateFromIpPort(customPublicIP, customPublicPort);
} else {
Log.Warn("Unable to parse 'Custom Public IP'");
}
}
return runner.StartGame(new StartGameArgs() {
SessionName = SessionName,
GameMode = GameMode.Server,
SceneManager = runner.gameObject.AddComponent<NetworkSceneManagerDefault>(),
Scene = (int)SceneDefs.CLIENTGAME,
SessionProperties = customProps,
Address = NetAddress.Any(port),
CustomPublicAddress = externalAddr,
CustomLobbyName = customLobby,
CustomPhotonAppSettings = photonSettings,
});
}
}
}
Buildした後は、linuxの場合、Dockerを使ってイメージ化が必要
docker build -t [yourplayfabuserIDforRegistory]/[yourgamename]:1.0
docker push [yourplayfabuserIDforRegistory]/[yourgamename]:1.0
Pushすると、PlayfabMultiplayerの管理画面でOSをLinuxにした場合に選択できる。
Dockerfile
# base image
FROM ubuntu:bionic
# installRUN apt-get --yes update && \
apt-get --yes clean && \
apt-get --yes install sudo
# add and setup fusion user
RUN useradd -m fusion && \
echo "fusion:fusion" | chpasswd && \
adduser fusion sudo
# copy server binary files
COPY --chown=fusion:fusion bin /home/fusion/bin
# set permissions on entrypoint
RUN chmod +x /home/fusion/bin/entrypoint.sh
# execute container as this user
USER fusion
# setup start scriptENTRYPOINT ["/home/fusion/bin/entrypoint.sh"]
# Fusion Server Port
EXPOSE 27015/udp
一旦疲れたのでここで終了。
他の方がめっちゃ丁寧に文章を書いてくれてるんだなと、改めてすごいと思う。
いつもありがとうございます。