공부/Unity

[Unity] Photon과 aws를 이용한 멀티 설정

굴러다니다니 2023. 6. 15. 17:03
728x90

0. aws, Photon 사이트 들어가서 가입해두기!

1. aws  설정

 

aws 접속해서 검색창에 EC2

 

EC2를 누른 후 인스턴스 시작 누르기!

 

대충 윈도우 선택해주고 (이 사진 위에 이름 쓸 수 있어요 이름 쓰기 -> 저는 Photon_Test_Server 썼습니다잉)

그리구 버전을 Microsoft Windows Server 2019 Base로 설정했ㅅㅂㅁ다

키 페어를 만들어줍니다! 대충 만들고 기억해두기~ 약속!

그다음 오른쪽에 인스턴스 시작 눌러주기

 

 

인스턴스창에 들어가면 위와같이 뜰텐데 파란색 인스턴스 ID를 눌러주자

 

들어가서 오른쪽 위에 연결 눌러주기~

 

RDP 클라이언트 들어가서 원격 데스크톱 파일 다운로드 해줍니다 (test_server) 다음 다시 인스턴스 창에서 인스턴스 ID 눌러주기

그리고 아래 암호 가져오기를 눌러주자

키페어에 연결된 인스턴스 ID 저거 옆에 복사 버튼 누르기~ (저장해두자)

 

들어가서 살짝 내려주면 보안에 보안 그룹이 뜨는데 눌러주고

 

나는 미리 설정해놨지만 인바운드 규칙이 아마 하나만 있을텐데 이를 설정해주기 위해 인바운드 규칙 편집을 눌러주자

인바운드: 클라이언트에서 서버로 접근

 

 

게임 서버에서 마스터 서버로 접근하기 위한 포트번호를 4520, 프로토콜을 TCP로 추가해주고 오른쪽의 사용자 지정 부분을 anyway로 바꿔주면 0.0.0.0/0가 추가된다.

마찬가지로 클라이언트에서 마스트 서버로 오기 위한 5055, 5056와 DataBase 연동을 위한 3306을 추가해준다.

규칙 저장을 눌러서 저장끝!


2. Photon 설정

아까 위에서 다운로드 받은 test server 원격 데스크톱 파일을 눌러서 들어가고 아까 키패드 설정한거 입력하구 뭐시기 하면 가상 컴퓨터가 뜬다! + 아까 복붙해둔 비밀번호도 써주기

 

photon 사이트에 접속해 로그인 한 후, Dashboard를 누르고 Applications > Self-Hosted를 눌러준다

최대 100명만 수용 가능하지만 무료인 서버 왼쪽을 눌러준담 -> 라이센스 획득!

그다음은 SDKs를 누르고 server를 눌러준다

 

오른쪽에 서버 클릭 > sdk 다운로드 옆에 링크있는거 눌러서 sdk파일 zip으로 된거 다운로드

다운받은 SDK 파일을 압축 해제해준다음

C:\Users\Administrator\Downloads\(서버이름)_v5-0-12-24499-rc1\deploy\bin_Win64

에 들어가 아까 다운받아준 라이센스를 넣어준다.

이런식 유노

 

다음으로는 현재 다운받은 SDK 파일들의 기본 설정된 IP들을 현재 서버를 연 IP로 바꿔줄 것이다.

 

배경화면에 존재하는 public ipv4 ip를 복붙해놓으세욤

저기 저 친구를 복붙해서 메모장에 존재하는 친구들을 다 갈아끼워줄겁니다.

localhost나 127.0.0.1 이라는 게 써있는 부분들을 다 저 주소로 바꿔주세요

 

총 3가지 config 파일들을 확인할겁니다

C:\Users\Administrator\Downloads\photon-server-sdk_v5-0-12-24499-rc1\deploy\LoadBalancing\Master\bin\Master.xml

C:\Users\Administrator\Downloads\photon-server-sdk_v5-0-12-24499-rc1\deploy\LoadBalancing\GameServer\bin\GameServer.xml.config

C:\Users\Administrator\Downloads\photon-server-sdk_v5-0-12-24499-rc1\deploy\NameServer\bin\NameServer.xml

세 친구들을 확인해서 모두 꼼꼼히 바꿔줍시당

 

C:\Users\Administrator\Downloads\(서버이름)_v5-0-12-24499-rc1\deploy\bin_Win64

PhotonControl 실행해줍시다 (뭐 확인 그런거 안뜨고 끄기만 뜨면 more info > Run anyway 누르기)


 

3. Unity 실행!

이제 예시를 위한 프로젝트를 하나 불러올건데 대충 없으니깐 asset store에서 받아주자

 

그리고 유니티에서 포톤을 사용하기 위해 얘도 받아주자

그리고 하이어라키 창에서 Photon Server Settings를 찾아서 아까 만든 public ipv4 서버 주소를 저기에 써주고 Port에 5055, Use Name Server를 꺼줍시다

 

그 후 script로 PunManager를 만들어주고 하이어라키창에서 빈 오브젝트 생성 후 스크립트를 넣어줍시다

 

photon에서는 크게 서버와 로비, 룸이 있습니다!

서버는 접속하면 서버

로비는 카트라이더 로비창같은 대기 창

룸은 제대로된 게임이나 멀티 접속이 되는 룸!

그것을 와리가리 하는 것!

using System.Collections;
using System.Collections.Generic;
using UnityEngine;
using Photon.Pun;
using Photon.Realtime;
    
public class PUNManager : MonoBehaviourPunCallbacks
{
    //서버 접속부터 Master Server -> Lobby -> Room
    private readonly string gameversion = "1";
    public ServerSettings setting = null;

    //플레이어 프리팹
    public GameObject playerPrefabs;

    private void Start()
    {
        Connect();
    }
    private void OnApplicationQuit()
    {
        Disconnect();
    }
    #region 서버 관련 콜백 함수들
    //ConnecttoMaster
    public void Connect()
    {
        PhotonNetwork.GameVersion = gameversion;
        setting.AppSettings.Server = DBManager.instance.ServerIP;

        //Master 서버에 연결
        PhotonNetwork.ConnectToMaster(setting.AppSettings.Server, setting.AppSettings.Port, "");
        Debug.Log("Connect to Master Server");
    }
    public void Disconnect()
    {
        PhotonNetwork.Disconnect(); //포톤 서버와 연결 끊기
    }

    //콜백 함수
    public override void OnConnectedToMaster()
    {
        base.OnConnectedToMaster();
        Debug.Log("Connect to Master Server");
        PhotonNetwork.JoinLobby(); //대기실로 이동
    }
    public override void OnJoinedLobby()
    {
        Debug.Log("Enter to Lobby");
        base.OnJoinedLobby();
        PhotonNetwork.JoinRandomRoom();
    }

    public override void OnJoinRandomFailed(short returnCode, string message)
    {
        base.OnJoinRandomFailed(returnCode, message);
        Debug.Log("No empty Room");
        PhotonNetwork.CreateRoom(null, new RoomOptions { MaxPlayers = 5 });
        Debug.Log("Make Room");
    }

    public override void OnJoinedRoom()
    {
        base.OnJoinedRoom();
        Debug.Log("Joined Room");
        PhotonNetwork.Instantiate(playerPrefabs.name, Vector3.zero, Quaternion.identity);
    }

    #endregion
}

 

이렇게 써주고 하이어라키 창에서 플레이어를 찾아줍시다

 

플레이어 친구한테 위에 세개를 넣어주고요, settings가 존재하는 파일에 프리팹화 해서 하이어라키에서는 삭제해줍시다

 

PunManager에서는 다음 두가지를 할당해주면 끝납니다~!

 

끝!

+ DBManager 뭔가 싶으실까봐

using System.Collections;
using System.Collections.Generic;
using UnityEngine;
using LitJson;
using MySql.Data;
using MySql.Data.MySqlClient;
using System.IO;
using System;

public class Userinfo
{
    public string name { get; private set; }
    public string password { get; private set; }

    public Userinfo(string name, string password)
    {
        this.name = name;
        this.password = password;
    }
}

public class DBManager : MonoBehaviour
{
    public static DBManager instance = null;

    //config json path
    public string DBPath = string.Empty;
    public string ServerIP = string.Empty;

    //mySQL 변수들
    MySqlConnection connection;
    MySqlDataReader reader;

    public Userinfo info;

    private void Awake()
    {
        if (instance == null)
        {
            instance = this;
            DontDestroyOnLoad(gameObject);
        }
        else
        {
            Destroy(gameObject);
            return;
        }
        try
        {
            DBPath = Application.dataPath + "/Database";
            string ServerInfo = ServerSet(DBPath);
            if (ServerInfo == null)
            {
                Debug.Log("SQL Server Null");
                return;
            }
            connection = new MySqlConnection(ServerInfo);
            connection.Open();
            Debug.Log("SQL Server Open");
        }
        catch (Exception e)
        {
            Debug.Log(e.Message);
        }
    }
    public string ServerSet(string path)
    {
        if (!File.Exists(path))
        {
            Directory.CreateDirectory(path);
        }

        string jsonString = File.ReadAllText(path + "/config.json");
        JsonData item = JsonMapper.ToObject(jsonString);
        string serverInfo = string.Format("Server= {0}; Database={1}; Uid={2}; Pwd={3}; Port={4};CharSet=utf8;", item[0]["IP"].ToString(), item[0]["TableName"].ToString(), item[0]["ID"].ToString(), item[0]["PW"].ToString(), item[0]["PORT"].ToString());

        string jsonStringServer = File.ReadAllText(path + "/Server.json");
        JsonData itemServer = JsonMapper.ToObject(jsonStringServer);
        ServerIP = itemServer[0]["Server_IP"].ToString();
        Debug.Log(ServerIP);

        return serverInfo;
    }

    private bool ConnectionCheck(MySqlConnection connection)
    {
        if (connection.State != System.Data.ConnectionState.Open)
        {
            connection.Open();
            if (connection.State != System.Data.ConnectionState.Open)
            {
                return false;
            }
        }
        return true;
    }

    public bool Login(string id, string PW)
    {
        try
        {
            if (!ConnectionCheck(connection))
            {
                return false;
            }
            string sqlCommand = 
                string.Format(@"SELECT User_Name,U_Password FROM user_info
WHERE User_Name='{0}' AND U_Password='{1}';", id, PW);
            MySqlCommand cmd = new MySqlCommand(sqlCommand, connection);
            reader = cmd.ExecuteReader();
            if (reader.HasRows) //읽어온 데이터에 행이 한개 이상이면
            {
                while (reader.Read())
                {
                    string name = (reader.IsDBNull(0)) ? string.Empty : (string)reader["User_Name"].ToString();
                    string pass = (reader.IsDBNull(0)) ? string.Empty : (string)reader["U_Password"].ToString();

                    if (!name.Equals(string.Empty) || !pass.Equals(string.Empty))
                    {
                        //로그인 성공
                        info = new Userinfo(name, pass);
                        if (!reader.IsClosed) reader.Close();
                        return true;
                    }
                    else
                    {
                        //로그인 실패
                        break;
                    }
                } //while문 끝
            }//if문 끝
            if (!reader.IsClosed) reader.Close();
            return false;
        }
        catch (Exception e)
        {
            Debug.Log(e.Message);
            if (!reader.IsClosed) reader.Close();
            return false;
        }
    }
}

셋이 모인 모습 낄낄

728x90