question

Claire Rochelmeyer avatar image
Claire Rochelmeyer asked

GetLeaderboard returns 400 BadRequest: "The StatisticName field is required"

I've been moving my player stat update calls from the client to cloud script, but I'm running into this issue where the GetLeaderboard request is failing because it's "missing" the StatisticName field. The error logs out with this as the request:

{"StartPosition":0,"MaxResultsCount":1}

So StatisticName is getting lost somewhere and I don't know why.

CloudScript functions:

handlers.SubmitStatisticUpdate = function (args)
{
	if (args && args.hasOwnProperty("StatisticUpdate")) 
	{
		var statUpdate = args.StatisticUpdate;
		if (statUpdate.hasOwnProperty("StatisticName") && statUpdate.hasOwnProperty("Value"))
		{
			// Ensure there's already a valid leaderboard with this stat name
			// We do not want to create another leaderboard with whatever value was injected
			var statValidResult = ValidateStatistic(args);
			if (!statValidResult.Valid)
			{
				return { Success: false, Message: statValidResult.Message };
			}
			// Ensure the score "adds up"
			var scoreValidResult = ValidateScore(args);
			if (!scoreValidResult.Valid)
			{
				return { Success: false, Message: scoreValidResult.Message };
			}
			try
			{
				// Tell the server to update this Player's score for this Statistic
				var updateResult = server.UpdatePlayerStatistics(
					{
						PlayFabId: currentPlayerId,
						Statistics: [{ statUpdate }],
					});
				
				return { Success: true, Result: result };
			}
			catch(ex)
			{
				// If the update call failed, tell us why
				return { Success: false, Message: "UpdatePlayerStatistics failed: " + JSON.stringify(ex) };
			}
		}
		
		return { Success: false, Message: "Did not receive required StatisticName or Value parameters" };
	}
	
	return { Success: false, Message: "Did not receive required UpdateStatisticsRequest parameter" };
};
function ValidateStatistic(args)
{
	try
	{
		var result = server.GetLeaderboard(
			{
				StatisticName: args.StatisticName,
				StartPosition: 0,
				MaxResultsCount: 1,
			});
		
		return { Valid : true };
	}
	catch (ex)
	{
		return { Valid : false, Message: "Couldn't get Statistic: " + JSON.stringify(ex) };
	}
};
unity3dCloudScript
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

·
Rick Chen avatar image
Rick Chen answered

You have checked if args.StatisticUpdate exists in line 3, and checked if args.StatisticUpdate.StatisticName exists in line 6, but you pass the args to ValidateStatistic function in line 10 and used the args.StatisticName to call the GetLeaderboard API in line 50. You haven’t checked if the args.StatisticName exists.

You could replace the “args.StatisticName” with “args.StatisticUpdate.StatisticName” in line 50.

4 comments
10 |1200

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

Claire Rochelmeyer avatar image Claire Rochelmeyer commented ·

Hi Rick, thanks for your help. This was indeed the issue >.<

I'm having another problem now: the GetLeaderboard result is returning without issues even if the StatisticName doesn't correlate to a defined leaderboard. Is there a way via CloudScript to check whether a Leaderboard exists or not, as the UpdatePlayerStatistics request states "Statistics not currently defined will be added" which is not ideal if we are assuming that these parameters are not secure?

0 Likes 0 ·
Claire Rochelmeyer avatar image Claire Rochelmeyer Claire Rochelmeyer commented ·

To be clear, the result that it returns is

{"Leaderboard":[],"Version":0}

which I don't believe can be differentiated between a Leaderboard/Statistic that doesn't exist and a Leaderboard/Statisticthat has been created (via admin.CreatePlayerStatisticDefinition) but as yet has had no submissions to it from a player. I ideally don't want to create a dummy score for each leaderboard every time one is intentionally created/versioned, and I assume that PlayFab has a way of requesting if one exists or not, surely(!?), I just can't find it under the server api list.

0 Likes 0 ·
Claire Rochelmeyer avatar image Claire Rochelmeyer Claire Rochelmeyer commented ·
0 Likes 0 ·
Show more comments

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.