I have an online game where players get to shape the world in some way - eg. Ultima Online's housing, where you get to build your houses directly onto certain parts of the world map. These are changes that should persist over time as part of the persistent world.
At the same time, the design team are adding new content and amending old content to improve and extend the game for new players. They will do this on a development server first during testing and then later have to merge their work in with the players' "work" on the live server.
Assuming we fix the game design issues - eg. players can only build in designated areas, so they never clash geographically with designer edits - what are good ways to handle the data or arrange the data structures so as to avoid conflicts when new designer data is merged in with new player data?
Example 1: a player crafts a new type of item, and the game assigns the ID 123456 to it. Instances of that item all refer back to 123456. Now imagine the game designers have a similar system, and a designer creates a new item also numbered 123456. How can this be avoided?
Example 2: someone makes a popular mod that gives all your dragons a French accent. It includes a script with a new object called
assignFrenchAccent which they use to assign the new voice assets to each dragon object. But you are about to deploy your "Napoleon vs Smaug" DLC which has an object of the same name - how can you do this without a lot of customer service problems?
I've thought of the following strategies:
- You can use 2 separate files/directories/databases, but then your read operations are significantly complicated. "Show All Items" has to perform one read on the designer DB and one read on the player DB (and still has to distinguish between the 2, somehow.)
- You can use 2 different namespaces within one store, eg. using strings as the primary key and prefixing them with "DESIGN:" or "PLAYER:", but creating those namespaces may be non-trivial and dependencies aren't clear. (eg. In an RDBMS you may not be able to efficiently use strings as primary keys. You could use integers and allocate all the primary keys below a certain number, eg 1 million, to be designer data, and everything above that point to be player data. But that info is invisible to the RDBMS and foreign key links will cross the 'divide', meaning all tooling and scripts need to explicitly work around it.)
- You can always work on the same shared database in real-time, but performance may be poor and the risk of damage to player data may be enhanced. It also doesn't extend to games that run on more than 1 server with different world data.
- ...any other ideas?
It occurs to me that although this is primarily an issue for online games, the concepts may apply to modding too, where the community creates mods at the same time that the developers patch their game. Are any strategies used here to reduce the chance of mod breaking when new patches come out?
I've also tagged this as "version control" because on one level that's what this is - 2 branches of data development that need merging. Perhaps some insights might come from that direction.
EDIT - some examples added above to help clarify the problem. I am starting to think the issue is really one of namespacing, which could be implemented in a store via composite keys. That simplifies the merge strategy, at least. But there may be alternatives I'm not seeing.