question

paralysis avatar image
paralysis asked

GrantItemsToUsers CustomData - CloudScript

Hi All,

I'm struggling with a function I'm trying to write that would grant a User multiple items but also set the CustomData on the instanced item at the same time - I know the GrantItemsToUsers function will allow me to do this but I can figure out the syntax to use to get it working (Its errors in PlayFab saying "The ItemGrants field is required.")

I'd just like some input on how to go about setting up my code for this

I have a custom struct that I use for adding custom data such as CharacterData etc and want to do the same with the inventory items.

CloudScript:

handlers.GrantItemsToUsers = function (args, context) {
    var request = {
        ItemGrants: args.itemIDs
    }
    var result = server.GrantItemsToUsers(request);
    return result
}

My Code:

    public void StartCloudGrantUsersItems()
    {
        var request = new ItemGrantStruct[2];
        request[0] = new ItemGrantStruct { PlayFabId = PlayFabID, ItemId = "Axe001", Data = new RelicData { AttackSpeed = 11, Defence = 100 } };
        request[1] = new ItemGrantStruct { PlayFabId = PlayFabID, ItemId = "Axe001", Data = new RelicData { AttackSpeed = 11, Defence = 4 } };
        var jsonRequest = JsonUtility.ToJson(request);
        Debug.Log("REQUEST: " + request);
        Debug.Log("REQUEST: " + jsonRequest);
        PlayFabClientAPI.ExecuteCloudScript(new ExecuteCloudScriptRequest()
        {
            FunctionName = "GrantItemsToUsers", // Arbitrary function name (must exist in your uploaded cloud.js file)
            FunctionParameter = new { itemIDs = jsonRequest }, // The parameter provided to your function
            GeneratePlayStreamEvent = true, // Optional - Shows this event in PlayStream
        }, OnStartCloudGrantUserItems, OnErrorShared);
    }

Probably not the most elegant code so I'd be happy for anyone to offer up a better way to achieve the end result

RelicData is just a struct with a load of fields in it

ItemGrantScruct is a struct with PlayFabId, ItemId and RelicData (Instead of a Dictionary that the standard ItemGrant requires)

Many Thanks in advance!

CloudScriptIn-Game Economy
2 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.

Gosen Gao avatar image Gosen Gao commented ·

May I see the logs generated by line 8 of the second code snippet?

0 Likes 0 ·
paralysis avatar image paralysis Gosen Gao commented ·

Hi, Yeah of course!

That line actually returns:

REQUEST: {}

Im an idiot for leaving that in as it was a last effort to get it working before bed last night before I gave up!

Going a step back with this code:

var requestTemp = new ItemGrantStruct { PlayFabId = PlayFabID, ItemId = "Axe001", Data = new RelicData { AttackSpeed = 11, Defence = 4 } };
var jsonRequest = JsonUtility.ToJson(requestTemp);
Debug.Log("TEMP REQUEST: " + requestTemp);

Returns:

TEMP REQUEST: {"Data":{"RelicName":"","Type":0,"Rarity":0,"AttacksPerSec":0.0,"AttackSpeed":11.0,"MagicDamage":0.0,"MeleeDamage":0.0,"Range":0.0,"Defence":4.0},"ItemId":"Axe001","PlayFabId":"XXXXXXXXXXXXX"}

Which I figured all I need to do now is to get that into an array, Right?

Thanks

0 Likes 0 ·

1 Answer

·
Gosen Gao avatar image
Gosen Gao answered

You don't have to convert the request to JSON, using the original request should be fine. Here is my test code for your reference.

var request = new List<ItemGrantStruct>();
request.Add(new ItemGrantStruct { PlayFabId = result.PlayFabId, ItemId = "shield_level_5", Data = new RelicData { AttackSpeed = 11, Defence = 100 } });
request.Add(new ItemGrantStruct { PlayFabId = result.PlayFabId, ItemId = "shield_level_5", Data = new RelicData { AttackSpeed = 11, Defence = 4 } });
PlayFabClientAPI.ExecuteCloudScript(
    new ExecuteCloudScriptRequest
    {
        FunctionName = "CTsGrantItemsToUsers",
        FunctionParameter = new { itemGrants = request },
        GeneratePlayStreamEvent = true
    },
    Fresult =>
    {
        Debug.Log(Fresult.FunctionResult.ToString());
    },
    Ferror =>
    {
        Debug.Log(Ferror.GenerateErrorReport());
    });
handlers.CTsGrantItemsToUsers = function (args, context) {
    log.debug(args.itemGrants);
    let request = {
        ItemGrants: args.itemGrants
    }
    let result = server.GrantItemsToUsers(request);
    return result
};

Also, in a single request, you can only update 5 key/value pairs for one inventory item. Since you have 9 keys, the other 4 keys may require an additional request to update.

1 comment
10 |1200

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

paralysis avatar image paralysis commented ·

Thanks alot @Gosen Gao that appears to work!

Thinking about it now that makes sense as I assume the function auto serialises it so it was doing it twice!

Tested the code and now get the 5 key error so I'll rethink it.

Basically just want to save the items data to the instance so I guess I'll have to update each item as its granted using the UpdateUserInventoryItemCustomData call - Does this have the 5 key limit also?


Many thanks again

0 Likes 0 ·

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.