Sign In Register

How can we help you today?

Start a new topic

connecting extra data to entities

Hi! I would like to attach lots of specific data to players, teams, etc... What is the best way of doing that? For example, there are some extra properties in a CreateTeamRequest as scriptData. How to save that in a runtime collection that has the same id as the team in the system collection? Problem is that in the request cloud code the team is not created still and the response not having the provided scriptData. Also the team will not get an id if created with name and type. I would like an efficient solution where not the client generates the id.

1 person has this question

P.s.: The added data should be and will be frequently searched/filtered and optionally will be returned with the basic responses.

So after many trial and errors there is no solution to the problem without very ugly hacks.


Finally what I've settled with is saving the extra data and create a new CreateTeamRequest using the id from the extra data entry. To cancel the request so it won't try to create the team twice, I have set a scriptError with the original response and copied that into the scriptData in the CreateTeamResponse.

 

// ====================================================================================================
//
// Cloud Code for CreateTeamRequest, write your code here to customize the GameSparks platform.
//
// For details of the GameSparks Cloud Code API see https://docs.gamesparks.com/
//
// ====================================================================================================

var data = Spark.getData();


// TODO: eval scriptData
var scriptData = data.scriptData;


// save data
var extra_data = Spark.runtimeCollection("teamExtraData");
extra_data.save(scriptData);

// give id to team and that's it
data.teamId = scriptData._id["$oid"];

// another request as we need to know if the team can be created
var response = Spark.sendRequest({
  "@class": ".CreateTeamRequest",
  "teamId": data.teamId,
  "teamName": data.teamName,
  "teamType": data.teamType,
  "scriptData": {"ez":"valami"}
})

if( response.hasOwnProperty("error") ) {

    // remove extra data
    extra_data = Spark.runtimeCollection("teamExtraData");
    extra_data.findAndRemove({"_id": {"$oid": data.teamId }});

    // couldn't create team
    for (var property in response.error) {
        if (response.error.hasOwnProperty(property)) {
            Spark.setScriptError(property, response.error[property]);
        }
    }

} else {
    Spark.setScriptError("skip_request", response);
}

Spark.exit();


// ====================================================================================================
//
// Cloud Code for CreateTeamResponse, write your code here to customize the GameSparks platform.
//
// For details of the GameSparks Cloud Code API see https://docs.gamesparks.com/
//
// ====================================================================================================

var data = Spark.getData();

// save original response
var orig_response = Spark.getScriptError("skip_request");

// remove fake error with original response
Spark.removeScriptError("skip_request");
if(Object.keys(data.error).length === 0 && data.error.constructor === Object) {
    Spark.removeAllScriptErrors();
}

if( orig_response !== null ) { 
    Spark.setScriptData("response", orig_response);
}

Spark.exit();

 

 This is working but very ugly and error prone. Also it renders your framework absolutely unnecessary 'cause this could be a custom request.

The preferred way would be something like:

 

//
// request script

var scriptData = Spark.getData().scriptData;

var extra_data = Spark.runtimeCollection("teamExtraData");
extra_data.save(scriptData);

Spark.setData("teamId", scriptData._id["$oid"]);

//
// GS creates team with the set id and gives normal response
//

//
// response script with teamId and scriptData still set

if( Spark.hasScriptErrors() ) {
  var data = Spark.getData();
  var extra_data = Spark.runtimeCollection("teamExtraData");
  extra_data.findAndRemove({"_id": {"$oid": data.teamId }});
}

 Much cleaner and response can be processed normally by GS API and our code as well.

Hi RwB,


When you send a CreateTeamRequest you can leave the teamID field out completely and a mongo oid will be used. This will make sure the id is unique. This id will then be in the CreateTeamResponse which you can then use as the id of the document you are going to insert into your custom collection. It's always best to use a playerId or any unique id that ties the extra data back to the object that it was created from. You can pass extra data into the request via scriptData and pass it to the response at which point you can insert it into the custom collection using the new teams ID. For players you can set scriptData or privateData on the player object itself. If you plan to store lot of data on the player a runtime collection may suit your needs better. Challenges and Matches can have data set to them also. Let me know if you have any further questions.


Regards,

Liam

Oups, I have miss typed in my original post, but if leave the team id out then it will be created without it - yes, blank. Also I've stated that the original scriptData from the request is lost in the response. I think it can be copied in the request to the requests scriptData so it can be preserved for the response. But if the error is not set then the backend will not cancel the team creation what was already done in the script cause there is no way else to set the team id. Please provide a working solution that is proven to be working like I did in my previous post so I can better understand how you do it and why it's not working for me. Thank you!

bump - I'd like to be able to set a public/private flag on a team when it's created and can't come up with a solution other than what RwB World has suggested above.

Login to post a comment