question

Yichen Wang avatar image
Yichen Wang asked

Photon Authentication Token Changes

I have looked and followed your documentation on how to request photon authentication token with PlayFab, and it worked. I have a question though. Every time a launch a photon room and finish a game and come back to the Home Screen, PlayFab reauthenticates and gives a new photon token, is it normal to have more than one photon token per session? I tried to put the script on don't destroy on load but it doesn't work. I am using signing in with email option on playfab to get a photon token authwithphoton with playfabidcache as the username and photon token as the token. Thanks in advance for the help.

Here is my authentication code, I tried to put it on don't destroy on load but it disconnects all my game objects for some reason:

using System.Collections;
using System.Collections.Generic;
using PlayFab;
using PlayFab.ClientModels;
using UnityEngine;
using PlayFab.PfEditor.Json;
using UnityEngine.UI;
using Photon.Pun;
using Photon.Realtime;
using UnityEngine.SceneManagement;


public class PlayFabController : MonoBehaviour
{
    private string _playFabPlayerIdCache;


    public static PlayFabController PFC;


    public PhotonRoom photonRoom;


    private string userEmail;
    private string userPassword;
    private string username;
    public GameObject loginPanel;
    public GameObject addLoginPanel;
    public GameObject recoverButton;
    public GameObject accessLeaderboardButton;
    public Button battleButton;
    public Button gatherResourcesButton;


    public void Start()
    {
        if (string.IsNullOrEmpty(PlayFabSettings.staticSettings.TitleId))
        {
            PlayFabSettings.staticSettings.TitleId = "74D5C";
        }


        if (PlayerPrefs.HasKey("EMAIL") && PlayerPrefs.HasKey("PASSWORD"))
        {
            userEmail = PlayerPrefs.GetString("EMAIL");
            userPassword = PlayerPrefs.GetString("PASSWORD");


            var request = new LoginWithEmailAddressRequest { Email = userEmail, Password = userPassword };
            PlayFabClientAPI.LoginWithEmailAddress(request, OnLoginSuccess, OnLoginFailure);
        }
        else
        {
#if UNITY_IOS
            var requestIOS = new LoginWithIOSDeviceIDRequest { DeviceId = ReturnMobileID(), CreateAccount = true };
            PlayFabClientAPI.LoginWithIOSDeviceID(requestIOS, OnLoginIOSSuccess, OnLoginIOSFailure);
#endif
        }
    }


    #region Login


    private void OnLoginSuccess(LoginResult result)
    {
        Debug.Log("Login Successful. Requesting Photon Token.");
        PlayerPrefs.SetString("EMAIL", userEmail);
        PlayerPrefs.SetString("PASSWORD", userPassword);
        loginPanel.SetActive(false);
        recoverButton.SetActive(false);
        GetStatistics();


        _playFabPlayerIdCache = result.PlayFabId;
        GetPhotonAuthenticationTokenRequest request = new GetPhotonAuthenticationTokenRequest();
        request.PhotonApplicationId = PhotonNetwork.PhotonServerSettings.AppSettings.AppIdRealtime;


        PlayFabClientAPI.GetPhotonAuthenticationToken(request, AuthWithPhoton, Error);
    }


    public void AuthWithPhoton(GetPhotonAuthenticationTokenResult obj)
    {
        var CustomAuth = new AuthenticationValues { AuthType = CustomAuthenticationType.Custom };


        CustomAuth.AddAuthParameter("username", _playFabPlayerIdCache);
        CustomAuth.AddAuthParameter("token", obj.PhotonCustomAuthenticationToken);


        PhotonNetwork.AuthValues = CustomAuth;


        Debug.Log("Photon token acquired " + obj.PhotonCustomAuthenticationToken + " authentication complete");


        battleButton.interactable = true;
        gatherResourcesButton.interactable = true;
    }


    public void Error(PlayFabError error)
    {
        Debug.LogError(error.GenerateErrorReport());
    }


    private void OnLoginFailure(PlayFabError error)
    {
        loginPanel.SetActive(false);
        addLoginPanel.SetActive(true);
        Debug.Log("Please Signup");
    }


    private void OnLoginIOSSuccess(LoginResult result)
    {
        Debug.Log("IOS Login Successful");
        recoverButton.SetActive(true);
        GetStatistics();
    }


    private void OnLoginIOSFailure(PlayFabError error)
    {
        Debug.Log(error.GenerateErrorReport());
        loginPanel.SetActive(true);
    }


    public void GetUserEmail(string emailIn)
    {
        userEmail = emailIn;
    }


    public void GetUserPassword(string passwordIn)
    {
        userPassword = passwordIn;
    }


    public void GetUsername(string usernameIn)
    {
        username = usernameIn;
    }


    public void OnClickLogin()
    {
        var request = new LoginWithEmailAddressRequest { Email = userEmail, Password = userPassword };
        PlayFabClientAPI.LoginWithEmailAddress(request, OnLoginSuccess, OnLoginFailure);
    }


    public void OnClickGoToSignup()
    {
        loginPanel.SetActive(false);
        addLoginPanel.SetActive(true);
    }


    public void OnClickBack()
    {
        loginPanel.SetActive(true);
        addLoginPanel.SetActive(false);
    }


    public static string ReturnMobileID()
    {
        string deviceID = SystemInfo.deviceUniqueIdentifier;
        return deviceID;
    }


    public void OpenAddLogin()
    {
        loginPanel.SetActive(true);
        recoverButton.SetActive(false);
    }


    public void OnClickAddLogin()
    {
        var addLoginRequest = new AddUsernamePasswordRequest { Email = userEmail, Password = userPassword, Username = username };
        PlayFabClientAPI.AddUsernamePassword(addLoginRequest, OnAddLoginSuccess, OnAddLoginFailure);
    }


    private void OnAddLoginSuccess(AddUsernamePasswordResult result)
    {
        Debug.Log("Login Added");
        PlayerPrefs.SetString("USERNAME", username);
        PlayerPrefs.SetString("EMAIL", userEmail);
        PlayerPrefs.SetString("PASSWORD", userPassword);


        PlayFabClientAPI.UpdateUserTitleDisplayName(new UpdateUserTitleDisplayNameRequest { DisplayName = username }, OnDisplayName, OnLoginIOSFailure);


        addLoginPanel.SetActive(false);
        GetStatistics();
    }


    void OnDisplayName(UpdateUserTitleDisplayNameResult result)
    {
        Debug.Log(result.DisplayName + "is your display name.");
    }


    private void OnAddLoginFailure(PlayFabError error)
    {
        Debug.LogWarning("Something went wrong with registering an account.  :(");
        Debug.LogError("Here's some debug information:");
        Debug.LogError(error.GenerateErrorReport());
    }


    #endregion Login


    public int playerHealth;
    public int playerDamage;


    public int playerTrophies;
    public int playerKillCount;
    public int playerLeage;


    public Text trophyCount;


    #region PlayerStats


    public void SetStatistics()
    {
        PlayFabClientAPI.UpdatePlayerStatistics( new UpdatePlayerStatisticsRequest
        {
            // request.Statistics is a list, so multiple StatisticUpdate objects can be defined if required.
            Statistics = new List<StatisticUpdate> {
                new StatisticUpdate { StatisticName = "playerHealth", Value = playerHealth },
                new StatisticUpdate { StatisticName = "playerDamage", Value = playerDamage },
                new StatisticUpdate { StatisticName = "playerTrophies", Value = playerTrophies },
                new StatisticUpdate { StatisticName = "playerKillCount", Value = playerKillCount },
                new StatisticUpdate { StatisticName = "playerLeage", Value = playerLeage },
            }
        },
        result => { Debug.Log("User statistics updated"); },
        error => { Debug.LogError(error.GenerateErrorReport()); });
    }


    void GetStatistics()
    {
        PlayFabClientAPI.GetPlayerStatistics(
            new GetPlayerStatisticsRequest(),
            OnGetStatistics,
            error => Debug.LogError(error.GenerateErrorReport())
        );
    }


    void OnGetStatistics(GetPlayerStatisticsResult result)
    {
        Debug.Log("Received the following Statistics:");
        foreach (var eachStat in result.Statistics)
        {
            Debug.Log("Statistic (" + eachStat.StatisticName + "): " + eachStat.Value);
            switch (eachStat.StatisticName)
            {
                case "playerHealth":
                    playerHealth = eachStat.Value;
                    break;
                case "playerDamage":
                    playerDamage = eachStat.Value;
                    break;
                case "playerTrophies":
                    playerTrophies = eachStat.Value;
                    trophyCount.text = playerTrophies.ToString();
                    break;
                case "playerKillCount":
                    playerKillCount = eachStat.Value;
                    break;
                case "playerLeage":
                    playerLeage = eachStat.Value;
                    break;
            }
        }
    }


    // Build the request object and access the API
    public void StartCloudUpdatePlayerStatistics()
    {
        PlayFabClientAPI.ExecuteCloudScript(new ExecuteCloudScriptRequest()
        {
            FunctionName = "UpdatePlayerStats", // Arbitrary function name (must exist in your uploaded cloud.js file)
            FunctionParameter = new { playerHealth = playerHealth,
                playerDamage = playerDamage,
                playerTrophies = playerTrophies,
                playerKillCount = playerKillCount,
                playerLeage = playerLeage}, // The parameter provided to your function
            GeneratePlayStreamEvent = true, // Optional - Shows this event in PlayStream
        }, OnCloudUpdateStatistics, OnErrorShared);
    }
    // OnCloudHelloWorld defined in the next code block


    private void OnCloudUpdateStatistics(ExecuteCloudScriptResult result)
    {
        // CloudScript returns arbitrary results, so you have to evaluate them one step and one parameter at a time
        Debug.Log(JsonWrapper.SerializeObject(result.FunctionResult));
        PlayFab.Json.JsonObject jsonResult = (PlayFab.Json.JsonObject)result.FunctionResult;
        object messageValue;
        jsonResult.TryGetValue("messageValue", out messageValue); // note how "messageValue" directly corresponds to the JSON values set in CloudScript
        Debug.Log((string)messageValue);


        trophyCount.text = playerTrophies.ToString();
    }


    private static void OnErrorShared(PlayFabError error)
    {
        Debug.Log(error.GenerateErrorReport());
    }


    #endregion PlayerStats


    public GameObject leaderboardPanel;
    public GameObject listingPrefab;
    public Transform listingContainer;


    #region Leaderboard


    public void GetLeaderboard()
    {
        var requestLeaderboard = new GetLeaderboardRequest { StartPosition = 0, StatisticName = "playerTrophies", MaxResultsCount = 10 };
        PlayFabClientAPI.GetLeaderboard(requestLeaderboard, OnGetLeaderboard, OnErrorLeaderboard);
    }


    void OnGetLeaderboard(GetLeaderboardResult result)
    {
        leaderboardPanel.SetActive(true);
        foreach (PlayerLeaderboardEntry player in result.Leaderboard)
        {
            GameObject tempListing = Instantiate(listingPrefab, listingContainer);
            LeaderboardListing LL = tempListing.GetComponent<LeaderboardListing>();
            LL.playerNameText.text = player.DisplayName;
            LL.playerTrophiesText.text = player.StatValue.ToString();
            Debug.Log(player.DisplayName + ": " + player.StatValue);
        }
    }


    public void CloseLeaderboardPanel()
    {
        accessLeaderboardButton.SetActive(true);
        leaderboardPanel.SetActive(false);
        for (int i = listingContainer.childCount - 1; i >= 0; i--)
        {
            Destroy(listingContainer.GetChild(i).gameObject);
        }
    }


    void OnErrorLeaderboard(PlayFabError error)
    {
        Debug.Log(error.GenerateErrorReport());
    }


    #endregion Leaderboard


    #region BattleButton


    public void StartPhoton()
    {
        SceneManager.LoadScene(2);
    }


    #endregion BattleButton


    #region GatherResourcesButton


    public void StartEndlessRunner()
    {
        SceneManager.LoadScene(1);
    }


    #endregion GatherResourcesButton
}


Authenticationphoton
10 |1200

Up to 2 attachments (including images) can be used with a maximum of 512.0 KiB each and 1.0 MiB total.

1 Answer

·
Seth Du avatar image
Seth Du answered

According to your description, though I am not very familiar with Photon, the re-authentication should be unnecessary. Defined by the PlayFab Unity SDK, when a player is logged in successfully, there will be a Game Object named as PlayFabHttp, which is already configured as “don’t destroy on load”, and it is used to store the login identity.

I don't see any uses of PlayFabController PFC. I assume it should be a defined singleton object. The re-authentication should be caused by repeated initialization. Please refer to these threads to define the Singleton:

10 |1200

Up to 2 attachments (including images) can be used with a maximum of 512.0 KiB each and 1.0 MiB total.

Write an Answer

Hint: Notify or tag a user in this post by typing @username.

Up to 2 attachments (including images) can be used with a maximum of 512.0 KiB each and 1.0 MiB total.