What is the best way to store Item identificators?

Hey everybody,
I am working on massive Inventory system and I am wondering what is the best way to store Item identificators so it is almost impossible to “duplicate the same id” for any player in the game.

I’ve seen before systems like some Discord bots/social sites uses they are basically storing ids by adding symbols in numerical/alphabetic order to them to prevent duplicates.

E.g:

local PreviousID = "1a"
local NewID = "1b"
local IDafter = "1c" 
--// etc.

So I am not certainly sure how this method would work in Roblox so I came with idea myself and I am asking if its really the best method how to prevent duplicates and also store low amount of data.

My idea:

local Player = ...
local Http = game:GetService("HttpService")
local GUID = Http:GenerateGUID(false)
local Conv = GUID:sub(1,9)
local ID = string.format("%s%s",Conv,Player.UserId)

Thank you for any contribution to this problem and I am sorry if thread on this topic already exist but I wasn’t able to find one, have a great day!

2 Likes

Not sure I grasp the nature of duplication here - are your items intended to be globally unique or just unique to the current player? Could you provide your exact use case? I think I understand this to be globally unique but just looking for clarification to confirm that is the case.

You can use roblox’s GUID to get a random Key that is never going to be the same as previous ones. Read more about it here: HttpService | Roblox Creator Documentation

Example:

local HttpService = game:GetService("HttpService")
local UniqueKey = HttpService:GenerateGUID(false) -- false means that key won't be wrapped inside curved brackets

I feel like using GUID will be a good way to handle this but if your really are going to make a massive inventory system how are you going to deal with datastore limits? I feel like those long strings that are generated and especially with a addition of a array with item details, etc, are going to eat up limits very quickly.

Alright sorry for not stating this here in OP,
most usable example is server/(cross setver) trading + if by some case two same IDs are met I don’t want to rewrite the ID.

I’ve alread used it in my example but the problem is data cost of this method.

That’s the thing I am worried about.
(Well yes I can create bunch of new datastores but handling everything in one datastore is much more handy for me)

Adding another idea:
Date of “creation” of item + few random characters could be a good thing?

Are you sure you will ever reach a datastore limit because of this? The datastore limit is 4,000,000 bytes and lets assume one item is like 100 bytes of data then you can store a whole of 40k items.

With multiple players that’s going to hit the limit fast.
40k entries isn’t alot.

1 Like

I’m going to do some tests with different data and see how small I can make the data while still being unique. I’ll reply with anything I find.

1 Like

What does multiple players mean? Isn’t its like for inventory for one player? So each player that plays a game can have a 40k items. Since datastore is unique for every player.

I know your concerns but keep in mind I am looking for best method, I know about GUID that’s not the reason why this post was created.

Also keep in mind that there is multiple Inventory systems not just one and each item requires different complexity of saving e.g. custom functions of each item etc.

If your cross-server trading system is only intended to be active for players that are in the game at the time of the trade being conducted, I would just implement MessagingService here. The server of the player who initiates the trade should generate a trade ID and send it over to the other server to record related trade data. When the target player responds to the trade with the right ID, the decision is sent back over and the data for the involved players is modified on their respective servers.

Maybe? If the trade is intended to be held long term like Roblox trades then it’s probably feasible to not have to bother with a unique ID and instead deliver the trades directly into a player’s data set which also involves MessagingService. If the target player is not in any game server at the time of the initiating player sending the trade, backlog it to a trades table in the target player’s data which they can view when they next log on. If they’re in the server, send it directly and log it just in case they leave before responding to the initiating player’s trade.

ProfileService and its global updates feature would be good for something like this.

I’ve never worked with trading personally but I feel like a workflow like this sounds realistic.

With some testing I have found out that:

Array: +2 bytes
GUID: 38 bytes
String: 3 bytes (Per character)
Int: 1 byte (Per character)

With some simple math the maximum amount of entries you can have using GUID would be 105263
And using your example you can have 190476 entries (This may vary depending on the GUID and UserId).

You can test your entries data usage by using JSONEncode()
Size = string.len(HttpService:JSONEncode(Id))

Adding onto this I have also found a post and module that provides some good information and how using binary may be a good option:

1 Like

I am using ProfileService and I forgot that functionality exists :smiley: but back to my problem you’ve never directly mentioned the duplication problematic that should be solved by unique ids that are the main topic of this thread.

(Yeah I am very paranoid about duplication glitches)

Thank you so much for this I’ll let you know what I can do with it (I am also aware how to check the data size that’s probably why I am here anyways :D)

1 Like

I would figure that duplication, either of a trade request or an item, is naturally resolvable by failing requests if the same id is passed around. If you’re writing directly into a player’s data set then your uniqueness is the initiating player’s id and if the initiator already has a pending trade with the target then there realistically shouldn’t be a need to accept a request for another trade, right?

Yeah that’s what GUID solves - but imagine not using data expensive GUID and possibility of two players with same IDs of items in their inventory not being able to trade that leads to bad UX and probably not coming back to the game ever again.

The extent of uniqueness in a trading system should only be as far as the id of the trade and that uniqueness only needs to be valid for as long as the trade is active. If you deliver the trade directly to another player’s data set then it’s already unique because it’s being directly delivered.

Item information, be it data or what is being offered in the trade only needs to be distinguishable if multiple of the same type of item can be offered. That’s all stuff that can be moved around and reconstructed when the trade is accepted. Items do not necessarily need uniqueness applied.

I think I’m starting to lose a scope on the main issue here, the reason for needing uniqueness, which part of the system is prone to duplication specifically and what said duplication may look like primarily because it feels like there’s too much focus on a specific point and not the general idea of what’s trying to be accomplished here.

A possibility is to store all currently active IDs within a separate datastore and when generating a new ID you can check if it already exists and if so just call the generation function again until you get a valid ID.

And regarding trades you can use different IDs within the trade and then deal with them later.

(Edit Colbert already stated this):

be it data or what is being offered in the trade only needs to be distinguishable if multiple of the same type of item can be offered. That’s all stuff that can be moved around and reconstructed when the trade is accepted. @colbert2677

Overall I think you are over thinking this issue. If the inventory system is really big as you say you may just need to use multiple datastores as one. There is only so small you can get when attempting to store unique data.

1 Like

Thank you for your thoughts and contribution on the problem yeah I now see that I might went a bit off-topic with the duplication but the main point of having unique ids are unfortunately this problem, if I don’t need trading I can just make simple checks when the player is getting the item “natural way” but with trading I need to carry about edge cases that can happen.

Thank you for all those informations as well I am looking through the module from Stravant that you sent here and it looks like the thing I need to have in order to create unique and not data expensive ids.

I wish I can give solution to both of you but I can’t unfortunately :smiley:.

1 Like

Thanks,

But also providing one more possible solution will be to save data under the players UserId with the addition of how many items have been created for that certain user. This will be small data wise due to being only and numbers and as well as being unique.

Example:

GeneratedId = tonumber("230520276".. 1)  --(2305202761)
GeneratedId2 = tonumber("230520276".. 2) --(2305202762)
GeneratedId14 = tonumber("230520276".. 14) --(23052027614)