Crafting service design question + ES


I am adding simple crafting mechanics to my game.

UI will look something like this

A list of crafting recipes will be displayed to the player and if the player has the required ingredients in his bag he can craft the item.

There is a CraftingService implemented with RMI. When the player selects to craft an item, the client-side service (CraftingClientService) will delegate the call to the server-side service (CraftingHostedService).

On the server-side service (CraftingHostedService), I need to first check if the player has the required items in his inventory and take them out then give him the crafted item.

An item has an InContainer(containerId) component that links it to the container it belongs to, in this case, it is the player bag.

It might sound like a stupid question but which of these approaches sounds right for this case. (checking if the player has the required items and take them)

1- Every time directly ask from EntityData (SqlEntityData):

EntityData ed;
EntityId playerBag;
Set<EntityId> items = ed.findEntities(Filters.fieldEquals(InContainer.class, "container", playerBag), InContainer.class, ObjectType.class, StackSize.class);

2- Ask from an InventorySystem that uses an EntitySet to watch for items with ObjectType and InContainer and StackSize component and keeps them in a Map:

// Keep track of items by container id
private final Map<EntityId, List<Entity>> itemsMap = new ConcurrentHashMap<>();

If the InventorySystem is the only thing that can add/remove things from the inventory then it’s ok to do the second.

Otherwise, I think you may open yourself up to strange exploits. Probably rare but any time you are caching data there is the chance that the cache will be slightly out of date if you aren’t super careful.

I always think back to the old Diablo bug (original Diablo, yes I’m that old) that let you clone items if you had a very specific pick-up/drop rhythm.

1 Like

Hmm, nope I can add/remove items from anywhere.

Oops! I see. I was not aware of the exploit. :wink:

Thanks for the help :slightly_smiling_face: