Player Inventory
1. What is Player Inventory?
The player inventory is designed to help you manage the in-game items of players. You can view and track the items purchased and received by players in their inventories.For security reasons, we only provide APIs that grant items to inventories for DS and virtual servers. You can also go to Portal -> Players to directly grant items to players.
2. Item Instances
When an item is granted to or purchased by a player and stored in the inventory for later use, it is instantiated as an item instance. Only normal items and container items can be instantiated.Item instances are associated with items through item IDs.
You can find the detailed definition of item instances in the FItemInstance structure of the PGOS SDK.
- instance_id: The unique identifier of an item instance in the player inventory.
- amount: For non-stackable items, the amount is always 1. For stackable items, the amount is an integer greater than or equal to 0.
- status: The instance status, which can be Available, Expired, Revoked, or Consumed.
- Only instances in the Available status are returned to the client through the GetInventoryItemInstances API.
- When an instance expires, its status changes to Expired.
- When an instance is deleted, its status changes to Revoked.
- When an instance is consumed, its status changes to Consumed.
- item: Property set inherited from the item.
- mutable_custom_data: The mutable custom data(key-value pairs) of the item instance, which can be set or increased by server. The mutable custom data key prefix must be one of "flt_", "int_", "str_", which indicates the type of value is
float
,int
orstring
. Max length of each key is 128, and max length of value is 4096. Max number of key-value pairs is 32. - mutable_custom_data_version: The version of mutable custom data, which would increase every time custom data changes.
- tags: The tags(key-value pairs) of the item instance, which can be set by client or server. Max length of each key is 128, and max length of value is 1024. Max number of key-value pairs is 32.
- created_time: The creation time of this item instance.
- updated_time: The updated time of this item instance.
- expired_time: The expiration timestamp of this item instance.
- time_to_live: The time this item instance remains in the player inventory, in seconds.
The figure below shows the instantiation and instance status conversion process:
3. Using the Player Inventory in the Portal
3.1 View Inventory
Go to Portal -> Players and find the desired player. In the Economy tab of the player details, you can view the player's inventory. The inventory shows the item instances owned by the player. On this page, you can:
- Filter the item instances displayed by item instance status.
- Search for item instances by item ID or instance ID.
- Place in-game items in players' inventory.
- Revoke an item instance.
3.2 Grant Items
In some circumstances, you may have to directly grant in-game items in a player's inventory. Go to Portal -> Players, find the desired player, and open the player inventory. Click +Grant In-game Items and set the items to grant.
You can grant multiple types of items at once and specify the quantity for each type:
3.3 Logs
PGOS keeps a log of all player inventory operations so you can easily track the flow of items in the game economy and the economic activities of players. Go to Portal -> Players, find the desired player, go to the Economy page, and click Logs. Click Log ID to view detailed information:
- Log ID: The log ID.
- Associated Log ID: Some inventory operations are associated with other operations, so the associated log ID must be recorded. Such operations include but are not limited to:
- Opening items granted from containers
- Granting items by bundles
- Operation: The action type, which can be Grant, Open, Consume, Revoke, or Expire.
- Item Instance: The object operated on. For example:
- When Operation = Grant, this is the granted item instance.
- When Operation = Open, this is the container item instance opened.
- Created Time: The creation time of the log.
4. Access Inventory with Client SDK
4.1 Acquire Player Inventory
This operation acquires all item instances in a player inventory, including available and expired item instances.
Interface prototype:
/**
* Get all item instances in the player's inventory.
*/
void GetInventory(TFunction<void(const FPgosResult& Ret, const FItemInstPack* Data)> Callback) const;
struct FItemInstPack
{
/** Item instances in the pack. */
TArray<FItemInstance> insts;
/** In-game item defines that may be referenced in the 'item_content', and you can use 'ItemDict::FindItem' to search. */
FItemDict item_dict;
};
Example Code:
#include "PgosSDKCpp.h"
void SomeUObjectClass::SomeFunction()
{
auto Economy = IPgosSDKCpp::Get().GetClientEconomyAPI();
if (Economy)
{
Economy->GetInventory([](const FPgosResult& Ret, const FItemInstPack* Data) {
if (Ret.err_code == (int32)Pgos::PgosErrCode::kSuccess)
{
UE_LOG(LogTemp, Log, TEXT("GetInventory Success"));
}
else
{
UE_LOG(LogTemp, Log, TEXT("GetInventory Failed: err_code=%d, err_msg=%s"), Ret.err_code, *Ret.msg);
}
});
}
}
4.2 Consume Item Instance
The operation consumes an item instance in the player inventory. Each time, the quantity consumed is 1. This API only applies to item instances with the property "ItemType=Normal".
Interface prototype:
/**
* Consume the specified item instance in the player's inventory.
*
* The virtual server bound to the consumer action will be triggered.
*
* @param Params Request params.
*/
void ConsumeInstance(
const FClientConsumeInstanceParams& Params,
TFunction<void(const FPgosResult& Ret, const FClientConsumeInstanceResult* Data)> Callback) const;
struct FClientConsumeInstanceParams : public FBaseBackendEventParams
{
/** The item instance id. */
FString instance_id;
/**
* [Optional] Used to ensure the idempotence of the function. Idempotence means that regardless of how many times the function is called, the result remains the same.
* By passing a unique `idempotency_token`, it ensures that the function does not produce duplicate side effects or results when called repeatedly.
* Note: To avoid generating the same idempotency_token as other players, it is recommended to concatenate it with the player's own player ID.
*/
FString idempotency_token;
};
struct FClientConsumeInstanceResult : public FClientInstanceOperationResult
{
/** The error code returned by the virtual server bound to the consumer action. */
int32 custom_err_code = 0;
/** The error msg returned by the virtual server bound to the consumer action. */
FString custom_err_msg;
/** The json string returned by the virtual server bound to the consumer action. */
FString func_result;
/**
* Whether the request is replayed.
* When it is True, it indicates that the result of the function is obtained by replaying with the same `idempotency_token`.
* This means that the result of the function has been generated in a previous call and is being reused in the current call.
*/
bool replayed = false;
};
struct FBaseBackendEventParams
{
/**
* [Optional] A game-defined custom value pass to PGOS backend event.
* If you need to get a custom value in the event, pass it in, otherwise, ignore this field.
* The size is limited to 4096 bytes (after converting the string to utf8 format).
* Detail for PGOS backend event: https://pgos.intlgame.com/pgosdoc/manual/service_manual/extensions/event.html.
* Detail for how to reference the 'event_custom_data':https://pgos.intlgame.com/pgosdoc/manual/service_manual/extensions/virtual_server_v2.html#43-the-request-and-response-protocol.
*/
FString event_custom_data;
};
Example Code:
#include "PgosSDKCpp.h"
void SomeUObjectClass::SomeFunction()
{
auto Economy = IPgosSDKCpp::Get().GetClientEconomyAPI();
if (Economy)
{
FClientConsumeInstanceParams Params;
Params.instance_id = TEXT("0e888750eb0444e2b5877f8e3e17c2d7");
// Params.idempotency_token = "player id" + "_" + "timestamp"
Economy->ConsumeInstance(Params, [](const FPgosResult& Ret, const FClientConsumeInstanceResult* Data) {
if (Ret.err_code == (int32)Pgos::PgosErrCode::kSuccess)
{
UE_LOG(LogTemp, Log, TEXT("ConsumeInstance Success"));
}
else
{
UE_LOG(LogTemp, Log, TEXT("ConsumeInstance Failed: err_code=%d, err_msg=%s"), Ret.err_code, *Ret.msg);
}
});
}
}
4.3 Open Container Instance
This operation opens a "Type=Container" item instance in the player inventory. The open quantity for each operation is 1. This API only applies to item instances with the property "ItemType=Container".
Interface prototype:
/**
* Open the specified container instance in the player's inventory.
*
* The PGOS backend events `event_item_revoked` and `event_item_granted`/`event_currency_changed` will be triggered.
*
* @param Params Request params.
*/
void OpenContainerInstance(
const FClientOpenContainerInstanceParams& Params,
TFunction<void(const FPgosResult& Ret, const FClientOpenContainerResult* Data)> Callback) const;
struct FClientOpenContainerInstanceParams : public FBaseBackendEventParams
{
/** The container instance id. */
FString instance_id;
};
struct FClientOpenContainerResult : public FClientInstanceOperationResult
{
/** The item instances obtained after opening the container. */
FItemInstPack item_insts;
/** The currencies obtained after opening the container. */
TArray<FCurrency> currencies;
};
struct FClientInstanceOperationResult
{
/** The instance id of this operation. */
FString instance_id;
/** The number of instance remaining after this operation. */
int32 left_amount = 0;
};
Example Code:
#include "PgosSDKCpp.h"
void SomeUObjectClass::SomeFunction()
{
auto Economy = IPgosSDKCpp::Get().GetClientEconomyAPI();
if (Economy)
{
FClientOpenContainerInstanceParams Params;
// fill Params
Economy->OpenContainerInstance(Params, [](const FPgosResult& Ret, const FClientOpenContainerResult* Data) {
if (Ret.err_code == (int32)Pgos::PgosErrCode::kSuccess)
{
UE_LOG(LogTemp, Log, TEXT("OpenContainerInstance Success"));
}
else
{
UE_LOG(LogTemp, Log, TEXT("OpenContainerInstance Failed: err_code=%d, err_msg=%s"), Ret.err_code, *Ret.msg);
}
});
}
}
4.4 Revoke Item Instance
This operation revokes an item instance in the player inventory.
Interface prototype:
/**
* Revoke the specified item instance in the player's inventory.
*
* The PGOS backend event `event_item_revoked` will be triggered.
*
* @param Params Request params.
*/
void RevokeInstance(
const FClientRevokeInstanceParams& Params,
TFunction<void(const FPgosResult& Ret, const FClientInstanceOperationResult* Data)> Callback) const;
struct FClientRevokeInstanceParams : public FBaseBackendEventParams
{
/** The item instance id. */
FString instance_id;
};
struct FClientOpenContainerResult : public FClientInstanceOperationResult
{
/** The item instances obtained after opening the container. */
FItemInstPack item_insts;
/** The currencies obtained after opening the container. */
TArray<FCurrency> currencies;
};
Example Code:
#include "PgosSDKCpp.h"
void SomeUObjectClass::SomeFunction()
{
auto Economy = IPgosSDKCpp::Get().GetClientEconomyAPI();
if (Economy)
{
FClientRevokeInstanceParams Params;
// fill Params
Economy->RevokeInstance(Params, [](const FPgosResult& Ret, const FClientInstanceOperationResult* Data) {
if (Ret.err_code == (int32)Pgos::PgosErrCode::kSuccess)
{
UE_LOG(LogTemp, Log, TEXT("RevokeInstance Success"));
}
else
{
UE_LOG(LogTemp, Log, TEXT("RevokeInstance Failed: err_code=%d, err_msg=%s"), Ret.err_code, *Ret.msg);
}
});
}
}
4.5 Set Instance Tags
Update the tags
data of the specified item instance in the player's inventory.
Instance tags
can have up to 32 keys, with each key limited to 128 bytes and each value limited to 1024 bytes(in a narrow-character string).
Interface prototype:
/**
* Update the `tags` data of the specified item instance in the player's inventory.
* Instance `tags` can have up to 32 keys, with each key limited to 128 bytes and each value limited to 1024 bytes(in a narrow-character string).
*
* @param Params Request params.
*/
void SetInstanceTags(
const FClientSetInstanceTagsParams& Params,
TFunction<void(const FPgosResult& Ret, const FClientSetInstanceTagsResult* Data)> Callback) const;
struct FClientSetInstanceTagsParams
{
/** The item instance id. */
FString instance_id;
/** Update the data of the specified keys in the `tags`. If the key does not exist, it indicates inserting new data. */
TMap<FString, FString> update_data;
/** Delete the data of specified keys in the `tags`. The key from `update_data` cannot be included. */
TArray<FString> delete_keys;
};
struct FClientSetInstanceTagsResult
{
/** Latest `tags` of item instance. */
TMap<FString, FString> tags;
};
Example Code:
#include "PgosSDKCpp.h"
void SomeUObjectClass::SomeFunction()
{
auto Economy = IPgosSDKCpp::Get().GetClientEconomyAPI();
if (Economy)
{
FClientSetInstanceTagsParams Params;
// Fill params
Economy->SetInstanceTags(Params, [](const FPgosResult& Ret, const FClientSetInstanceTagsResult* Data) {
if (Ret.err_code == (int32)Pgos::PgosErrCode::kSuccess)
{
UE_LOG(LogTemp, Log, TEXT("SetInstanceTags Success"));
}
else
{
UE_LOG(LogTemp, Log, TEXT("SetInstanceTags Failed: err_code=%d, err_msg=%s"), Ret.err_code, *Ret.msg);
}
});
}
}
5. Manage Item Instances With Server SDK
5.1 Grant Item Instance
This operation grants a specified InGameItem to a specified player.
Interface prototype:
/**
* Grant specified items to the player's inventory.
*
* The PGOS backend events `event_item_granted`/`event_currency_changed` will be triggered.
*
* @param Params Request params.
*/
void GrantItemToPlayer(
const FServerGrantItemToPlayerParams& Params,
TFunction<void(const FPgosResult& Ret, const FServerGrantItemResult* Data)> Callback) const;
struct FServerGrantItemToPlayerParams : public FBaseBackendEventParams
{
/** The player id who will be granted items to. */
FString player_id;
/** The items will be granted. */
TArray<FServerGrantItem> items;
/**
* [Optional] Used to ensure the idempotence of the function. Idempotence means that regardless of how many times the function is called, the result remains the same.
* By passing a unique `idempotency_token`, it ensures that the function does not produce duplicate side effects or results when called repeatedly.
* Note: To avoid generating the same idempotency_token as other players, it is recommended to concatenate it with the `player_id`.
*/
FString idempotency_token;
};
struct FServerGrantItem {
/** The id of the item will be granted. */
pgos::pstring item_id;
/** The number of the item will be granted. */
uint32_t amount = 0;
/**
* The mutable kv data of the instance.
* The key must be prefixed with "int_", "flt_", or "str_", which respectively indicate that the value type is integer, float, or string.
* Max 32 keys, each key limited to 128 bytes and each value limited to 4096 bytes(in a narrow-character string).
*/
pgos::pmap<pgos::pstring, KVDataValue> mutable_custom_data;
};
struct FServerGrantItemResult
{
/** The player id who has been successfully granted. */
FString player_id;
/** The item instances that have been granted. */
FItemInstPack item_insts;
/** The currencies that have been granted. (such as granting bundle that contains currencies) */
TArray<FCurrency> currencies;
/**
* Whether the request is replayed.
* When it is True, it indicates that the result of the function is obtained by replaying with the same `idempotency_token`.
* This means that the result of the function has been generated in a previous call and is being reused in the current call.
*/
bool replayed = false;
};
Example Code:
#include "PgosSDKCpp.h"
void SomeUObjectClass::SomeFunction()
{
auto Economy = IPgosSDKCpp::Get().GetServerEconomyAPI();
if (Economy)
{
FServerGrantItemToPlayerParams Params;
// Fill Params
Economy->GrantItemToPlayer(Params, [](const FPgosResult& Ret, const FServerGrantItemResult* Data) {
if (Ret.err_code == (int32)Pgos::PgosErrCode::kSuccess)
{
UE_LOG(LogTemp, Log, TEXT("GrantItemToPlayer Success"));
}
else
{
UE_LOG(LogTemp, Log, TEXT("GrantItemToPlayer Failed: err_code=%d, err_msg=%s"), Ret.err_code, *Ret.msg);
}
});
}
}
5.2 Batch Revoke Instances
You can batch revoke the specified item instances in the player's inventory.
Interface prototype:
/**
* Batch revoke the specified item instances in the player's inventory.
*
* The PGOS virtual server event `event_item_revoked` will be triggered.
*
* @param Params Request params.
*/
void BatchRevokeInstances(
const FServerBatchRevokeInstancesParams& Params,
TFunction<void(const FPgosResult& Ret, const FServerBatchRevokeInstancesResult* Data)> Callback) const;
struct FServerBatchRevokeInstancesParams : public FBaseBackendEventParams
{
/** The player whose item instance will be revoked from inventory. */
FString player_id;
/** The item instance ids. Maximum array size: 99. */
TArray<FString> instance_ids;
};
struct FServerBatchRevokeInstancesResult
{
/** The number of instance remaining after this operation. key: item instance id, value: left amount. */
TMap<FString, int32> left_amounts;
/** Item instances that failed to revoke. key: item instance id, value: failed reason. */
TMap<FString, FPgosResult> fails;
};
Example Code:
#include "PgosSDKCpp.h"
void SomeUObjectClass::SomeFunction()
{
auto Economy = IPgosSDKCpp::Get().GetServerEconomyAPI();
if (Economy)
{
FServerBatchRevokeInstancesParams Params;
// Fill Params
Economy->BatchRevokeInstances(Params, [](const FPgosResult& Ret, const FServerBatchRevokeInstancesResult* Data) {
if (Ret.err_code == (int32)Pgos::PgosErrCode::kSuccess)
{
UE_LOG(LogTemp, Log, TEXT("BatchRevokeInstances Success"));
}
else
{
UE_LOG(LogTemp, Log, TEXT("BatchRevokeInstances Failed: err_code=%d, err_msg=%s"), Ret.err_code, *Ret.msg);
}
});
}
}
5.3 Search Player Inventory
You can search for item instances in an inventory by InstanceIds. If the InstanceIds parameter is blank, the player inventory is returned.
Interface prototype:
/**
* Query item instances in the specified player's inventory.
*
* @param PlayerId The specified player id.
* @param InstanceIds Item instance ids to query. If the 'instance_ids' is empty, it will return all instances in the player's inventory.
*/
void GetPlayerInventory(
const FString& PlayerId,
const TArray<FString>& InstanceIds,
TFunction<void(const FPgosResult& Ret, const FServerGetPlayerInventoryResult* Data)> Callback) const;
struct FServerGetPlayerInventoryResult
{
/** The player id whose inventory will be queried. */
FString player_id;
/** The item instances of the query instance ids. */
FItemInstPack item_insts;
/** The instance ids which was failed to query. */
TMap<FString, FString> fails;
};
Example Code:
#include "PgosSDKCpp.h"
void SomeUObjectClass::SomeFunction()
{
auto Economy = IPgosSDKCpp::Get().GetServerEconomyAPI();
if (Economy)
{
FString PlayerId;
TArray<FString> InstanceIds;
Economy->GetPlayerInventory(PlayerId, InstanceIds, [](const FPgosResult& Ret, const FServerGetPlayerInventoryResult* Data) {
if (Ret.err_code == (int32)Pgos::PgosErrCode::kSuccess)
{
UE_LOG(LogTemp, Log, TEXT("GetPlayerInventory Success"));
}
else
{
UE_LOG(LogTemp, Log, TEXT("GetPlayerInventory Failed: err_code=%d, err_msg=%s"), Ret.err_code, *Ret.msg);
}
});
}
}
5.4 Set Instance Custom Data
Update the mutable_custom_data
of the specified item instance in the player's inventory. When there are any changes to the mutable_custom_data
, its version number mutable_custom_data_version
will also be updated.
PGOS specifies the key format of mutable_custom_data
: the key must be prefixed with "int", "flt", or "str_", which respectively indicate that the value type is integer, float, or string.
The SetInstanceCustomData
and SetInstanceCustomDataWithVersion
APIs have some differences, and developers can choose which one to use based on their needs:
- When calling
SetInstanceCustomData
, there is no need to provide the version of themutable_custom_data
in the item instance; the data is updated directly. - When calling
SetInstanceCustomDataWithVersion
, it is mandatory to provide the latest version of themutable_custom_data
in the item instance; otherwise, the data cannot be updated.
Instance mutable_custom_data
can have up to 32 keys, with each key limited to 128 bytes and each value limited to 4096 bytes(in a narrow-character string).
Interface prototype:
/**
* Update the `mutable_custom_data` of the specified item instance in the player's inventory.
* The key must be prefixed with "int_", "flt_", or "str_", which respectively indicate that the value type is integer, float, or string.
* Instance `mutable_custom_data` can have up to 32 keys, with each key limited to 128 bytes and each value limited to 4096 bytes(in a narrow-character string).
*
* @param Params Request params.
*/
void SetInstanceCustomData(
const FServerSetInstanceCustomDataParams& Params,
TFunction<void(const FPgosResult& Ret, const FServerSetInstanceCustomDataResult* Data)> Callback) const;
/**
* Update the `mutable_custom_data` of the specified item instance in the player's inventory.
* The key must be prefixed with "int_", "flt_", or "str_", which respectively indicate that the value type is integer, float, or string.
* The 'version' that needs to be passed in can be obtained from the `mutable_custom_data` of the `ItemInstance`.
* If the 'version' passed in is the latest, the callback will return success along with the latest data after updated.
* If the 'version' passed in is not the latest, the callback will return failure(err_code=11108, kBackendKVDataVersionMismatched) along with the current latest data, you may try again with the latest version.
* Instance `mutable_custom_data` can have up to 32 keys, with each key limited to 128 bytes and each value limited to 4096 bytes(in a narrow-character string).
*
* @param Params Request params.
*/
void SetInstanceCustomDataWithVersion(
const FServerSetInstanceCustomDataWithVersionParams& Params,
TFunction<void(const FPgosResult& Ret, const FServerSetInstanceCustomDataResult* Data)> Callback) const;
/**
* Batch update the `mutable_custom_data` of the specified item instance in the player's inventory.
* The key must be prefixed with "int_", "flt_", or "str_", which respectively indicate that the value type is integer, float, or string.
* Instance `mutable_custom_data` can have up to 32 keys, with each key limited to 128 bytes and each value limited to 4096 bytes(in a narrow-character string).
*
* @param Params Request params.
*/
void BatchSetInstanceCustomData(
const FServerBatchSetInstanceCustomDataParams& Params,
TFunction<void(const FPgosResult& Ret, const FServerBatchSetInstanceCustomDataResult* Data)> Callback) const;
struct FServerSetInstanceCustomDataParams
{
/** The player whose item instance `mutable_custom_data` will be updated. */
FString player_id;
/** The item instance id. */
FString instance_id;
/** Update the data of the specified keys in the `mutable_custom_data`. If the key does not exist, it indicates inserting new data. */
TMap<FString, FKVDataValue> update_data;
/** Delete the data of specified keys in the `mutable_custom_data`. The key from `update_data` cannot be included. */
TArray<FString> delete_keys;
};
struct FServerSetInstanceCustomDataWithVersionParams : public FServerSetInstanceCustomDataParams
{
/** The latest `mutable_custom_data_version`. */
int32 version = 0;
};
struct FServerSetInstanceCustomDataResult
{
/** Latest `mutable_custom_data` of item instance. */
TMap<FString, FKVDataValue> mutable_custom_data;
/** Latest `mutable_custom_data_version` of item instance. */
int32 version = 0;
};
struct FServerBatchSetInstanceCustomDataParams
{
/** The player whose item instance `mutable_custom_data` will be updated. */
FString player_id;
/**
* The item instances to be updated. key: item instance id, value: custom data to be updated.
* Maximum map entries: 99.
*/
TMap<FString, FServerUpdatedInstanceCustomData> data;
};
struct FServerUpdatedInstanceCustomData
{
/** Update the data of the specified keys in the `mutable_custom_data`. If the key does not exist, it indicates inserting new data. */
TMap<FString, FKVDataValue> update_data;
/** Delete the data of specified keys in the `mutable_custom_data`. The key from `update_data` cannot be included. */
TArray<FString> delete_keys;
};
struct FServerBatchSetInstanceCustomDataResult
{
/** Latest `mutable_custom_data` of item instance. key: item instance id, value: latest custom data */
TMap<FString, FServerInstanceCustomData> data;
/** Item instances that failed to update. key: item instance id, value: failed reason. */
TMap<FString, FPgosResult> fails;
};
struct FServerInstanceCustomData
{
/** Latest `mutable_custom_data` of item instance. */
TMap<FString, FKVDataValue> mutable_custom_data;
/** Latest `mutable_custom_data_version` of item instance. */
int32 version = 0;
};
Example Code:
#include "PgosSDKCpp.h"
void SomeUObjectClass::SomeFunction()
{
auto Economy = IPgosSDKCpp::Get().GetServerEconomyAPI();
if (Economy)
{
FServerSetInstanceCustomDataParams Params;
// Fill params
Economy->SetInstanceCustomData(Params, [](const FPgosResult& Ret, const FServerSetInstanceCustomDataResult* Data) {
if (Ret.err_code == (int32)Pgos::PgosErrCode::kSuccess)
{
UE_LOG(LogTemp, Log, TEXT("SetInstanceCustomData Success"));
}
else
{
UE_LOG(LogTemp, Log, TEXT("SetInstanceCustomData Failed: err_code=%d, err_msg=%s"), Ret.err_code, *Ret.msg);
}
});
}
}
void SomeUObjectClass::SomeFunction2()
{
auto Economy = IPgosSDKCpp::Get().GetServerEconomyAPI();
if (Economy)
{
FServerSetInstanceCustomDataWithVersionParams Params;
// Fill params
Economy->SetInstanceCustomDataWithVersion(Params, [](const FPgosResult& Ret, const FServerSetInstanceCustomDataResult* Data) {
if (Ret.err_code == (int32)Pgos::PgosErrCode::kSuccess)
{
UE_LOG(LogTemp, Log, TEXT("SetInstanceCustomDataWithVersion Success"));
}
else
{
UE_LOG(LogTemp, Log, TEXT("SetInstanceCustomDataWithVersion Failed: err_code=%d, err_msg=%s"), Ret.err_code, *Ret.msg);
}
});
}
}
void SomeUObjectClass::SomeFunction3()
{
auto Economy = IPgosSDKCpp::Get().GetServerEconomyAPI();
if (Economy)
{
FServerBatchSetInstanceCustomDataParams Params;
// Fill Params
Economy->BatchSetInstanceCustomData(Params, [](const FPgosResult& Ret, const FServerBatchSetInstanceCustomDataResult* Data) {
if (Ret.err_code == (int32)Pgos::PgosErrCode::kSuccess)
{
UE_LOG(LogTemp, Log, TEXT("BatchSetInstanceCustomData Success"));
}
else
{
UE_LOG(LogTemp, Log, TEXT("BatchSetInstanceCustomData Failed: err_code=%d, err_msg=%s"), Ret.err_code, *Ret.msg);
}
});
}
}
5.5 Increase Instance Custom Data
Perform atomic increment operation on mutable_custom_data
kvdata for the instance. Only keys with the prefixes "int" and "flt" are supported.
Instance mutable_custom_data
can have up to 32 keys, with each key limited to 128 bytes and each value limited to 4096 bytes(in a narrow-character string).
Interface prototype:
/**
* Perform atomic increment operation on `mutable_custom_data` kvdata for the instance. [Only keys with the prefixes "int_" and "flt_" are supported]
*
* @param Params Request params.
*/
void IncrInstanceCustomData(
const FServerIncrInstanceCustomDataParams& Params,
TFunction<void(const FPgosResult& Ret, const FServerIncrInstanceCustomDataResult* Data)> Callback) const;
struct FServerIncrInstanceCustomDataParams
{
/** The player id whose item instance `mutable_custom_data` will be updated. */
FString player_id;
/** The item instance id. */
FString instance_id;
/** Increments to update, key: kvdata key, value: increment of the value. */
TMap<FString, FKVDataValue> increments;
/**
* [Optional] Used to ensure the idempotence of the function.
* By passing a unique `idempotency_token`, it ensures that the function does not produce duplicate side effects or results when called repeatedly.
*/
FString idempotency_token;
};
struct FServerIncrInstanceCustomDataResult
{
/** Latest `mutable_custom_data` of item instance. */
TMap<FString, FKVDataValue> mutable_custom_data;
/** Latest `mutable_custom_data_version` of item instance. */
int32 version = 0;
/**
* Whether the request is replayed.
* When it is true, it indicates that the previously used `idempotency_token` was used, and the increment operation did not take effect. The result returns the latest `mutable_custom_data` and `mutable_custom_data_version` of the instance.
*/
bool replayed = false;
};
Example Code:
#include "PgosSDKCpp.h"
void SomeUObjectClass::SomeFunction()
{
auto Economy = IPgosSDKCpp::Get().GetServerEconomyAPI();
if (Economy)
{
FServerIncrInstanceCustomDataParams Params;
// Fill params
Economy->IncrInstanceCustomData(Params, [](const FPgosResult& Ret, const FServerIncrInstanceCustomDataResult* Data) {
if (Ret.err_code == (int32)Pgos::PgosErrCode::kSuccess)
{
UE_LOG(LogTemp, Log, TEXT("IncrInstanceCustomData Success"));
}
else
{
UE_LOG(LogTemp, Log, TEXT("IncrInstanceCustomData Failed: err_code=%d, err_msg=%s"), Ret.err_code, *Ret.msg);
}
});
}
}
5.6 Set Instance Tags
Update the tags
data of the specified item instance in the player's inventory.
Instance tags
can have up to 32 keys, with each key limited to 128 bytes and each value limited to 1024 bytes(in a narrow-character string).
Interface prototype:
/**
* Update the `tags` data of the specified item instance in the player's inventory.
* Instance `tags` can have up to 32 keys, with each key limited to 128 bytes and each value limited to 1024 bytes(in a narrow-character string).
*
* @param Params Request params.
*/
void SetInstanceTags(
const FServerSetInstanceTagsParams& Params,
TFunction<void(const FPgosResult& Ret, const FServerSetInstanceTagsResult* Data)> Callback) const;
/**
* Batch update the `tags` data of the specified item instance in the player's inventory.
* Instance `tags` can have up to 32 keys, with each key limited to 128 bytes and each value limited to 1024 bytes(in a narrow-character string).
*
* @param Params Request params.
*/
void BatchSetInstanceTags(
const FServerBatchSetInstanceTagsParams& Params,
TFunction<void(const FPgosResult& Ret, const FServerBatchSetInstanceTagsResult* Data)> Callback) const;
struct FServerSetInstanceTagsParams
{
/** The player id whose item instance `tags` will be updated. */
FString player_id;
/** The item instance id. */
FString instance_id;
/** Update the data of the specified keys in the `tags`. If the key does not exist, it indicates inserting new data. */
TMap<FString, FString> update_data;
/** Delete the data of specified keys in the `tags`. The key from `update_data` cannot be included. */
TArray<FString> delete_keys;
};
struct FServerSetInstanceTagsResult
{
/** Latest `tags` of item instance. */
TMap<FString, FString> tags;
};
struct FServerBatchSetInstanceTagsParams
{
/** The player id whose item instance `tags` will be updated. */
FString player_id;
/**
* The item instances to be updated. key: item instance id, value: tags to be updated.
* Maximum map entries: 99.
*/
TMap<FString, FServerUpdatedInstanceTags> data;
};
struct FServerUpdatedInstanceTags
{
/** Update the data of the specified keys in the `tags`. If the key does not exist, it indicates inserting new data. */
TMap<FString, FString> update_data;
/** Delete the data of specified keys in the `tags`. The key from `update_data` cannot be included. */
TArray<FString> delete_keys;
};
struct FServerBatchSetInstanceTagsResult
{
/** Latest `tags` of item instance. */
TMap<FString, FServerInstanceTags> data;
/** Item instances that failed to update. key: item instance id, value: failed reason. */
TMap<FString, FPgosResult> fails;
};
struct FServerInstanceTags
{
/** Latest `tags` of item instance. */
TMap<FString, FString> tags;
};
Example Code:
#include "PgosSDKCpp.h"
void SomeUObjectClass::SomeFunction()
{
auto Economy = IPgosSDKCpp::Get().GetServerEconomyAPI();
if (Economy)
{
FServerSetInstanceTagsParams Params;
// Fill params
Economy->SetInstanceTags(Params, [](const FPgosResult& Ret, const FServerSetInstanceTagsResult* Data) {
if (Ret.err_code == (int32)Pgos::PgosErrCode::kSuccess)
{
UE_LOG(LogTemp, Log, TEXT("SetInstanceTags Success"));
}
else
{
UE_LOG(LogTemp, Log, TEXT("SetInstanceTags Failed: err_code=%d, err_msg=%s"), Ret.err_code, *Ret.msg);
}
});
}
}
void SomeUObjectClass::SomeFunction2()
{
auto Economy = IPgosSDKCpp::Get().GetClientEconomyAPI();
if (Economy)
{
FClientSetInstanceTagsParams Params;
Economy->SetInstanceTags(Params, [](const FPgosResult& Ret, const FClientSetInstanceTagsResult* Data) {
if (Ret.err_code == (int32)Pgos::PgosErrCode::kSuccess)
{
UE_LOG(LogTemp, Log, TEXT("SetInstanceTags Success"));
}
else
{
UE_LOG(LogTemp, Log, TEXT("SetInstanceTags Failed: err_code=%d, err_msg=%s"), Ret.err_code, *Ret.msg);
}
});
}
}
6. Key Errors Handling
Error Code | Relevant API | Handling Suggestion |
---|---|---|
kBackendGrantItemNumExceed | GrantItemToPlayer | Grant items num exceeds limit. |
kBackendThrottling | GrantItemToPlayer ConsumeInstance OpenContainerInstance | Too many operations for current player detected, please retry shortly. |
kBackendShouldRetry | GrantItemToPlayer | The failure request can be retried for a success. |
kBackendIdempotentParamsMismatch | GrantItemToPlayer | A idempotency_token input parameter was reused with an operation, but at least one of the other input parameters is different from the previous call to the operation. By now the error will be returned when player id is not consistent. |
kBackendDupCustomDataKey | SetInstanceTags SetInstanceCustomDataWithVersion SetInstanceCustomData | Duplicated key is detected in update data and delete keys, which might cause uncertain behavior. |
kBackendInvalidCustomData | SetInstanceTags SetInstanceCustomDataWithVersion SetInstanceCustomData IncrInstanceCustomData | Invalid custom data format. The custom data's prefix is invalid, or length of key and value, or number of keys exceeds the limit. |