Appearance
Appearance
Google Sheets is a very popular tool to manage game configuration data. Most designers are experienced in working with spreadsheets, the tool is free, supports live collaboration and requires no installation. The Metaplay SDK includes built-in support to securely import data from Google Sheets, but you could adapt this guide to import data from other sources.
At the end of this guide, you will have an end-to-end implementation of you custom game configs data being imported from Google Sheets.
The first thing you need to do is set up a spreadsheet with the contents of the config data you’ll add to your game. A sensible starting point is to add a sheet per config library with columns that map to the config item members.
For this example, we’re using TroopKinds
, the same example as in Introduction to Game Configs. You can do an intermission there if you have questions about formatting a config library spreadsheet or how configs work in general.
To fetch the spreadsheets, you need credentials from a Google Service account. Here’s a quick step-by-step:
The first thing you need to do is access Google Developer’s Console and either create a new project or select the project associated with your game if you already have one.
To allow your project access to your Google Sheets spreadsheets, you must enable the Google Drive and Google Sheets APIs. Click the “Enable APIs and Services” and search the API library for “Google Drive API” and “Google Sheets API.”
Then, you need a service account. Back in the “APIs & Services” dashboard, find “Credentials” on the leftmost menu and click it to access your project’s registered credentials.
On the “Credentials” page, find the “Create Credentials” button on the top and add a service account.
After creating and configuring the service account, find “Manage Service Accounts” back on the Credentials page.
On the right-hand side of the page, click “Actions” and select “Manage Keys**.”** There, you can create a new JSON key, download it, and add it to your project. Don’t forget to go to Google Sheets and allow your service account access to the spreadsheet! You can do that by sharing the spreadsheet with the account e-mail address.
For you to be able to fetch a spreadsheet from Google Sheets, you need the SpreadsheetId
. You can extract the ID from the Google Sheets spreadsheet URL, which is formatted as such:
https://docs.google.com/spreadsheets/d/**spreadsheetId**/edit#gid=0
You can then configure your DefaultGameConfigBuildParameters
to tell the SDK where you would like to fetch your configs from:
public class MyGameConfigBuildIntegration : GameConfigBuildIntegration
{
// If only using a single source in config builds you can disregard the "sourceProperty" parameter.
public override IEnumerable<GameConfigBuildSource> GetAvailableGameConfigBuildSources(string sourceProperty)
{
return new[]
{
// Spreadsheet IDs go here:
new GoogleSheetBuildSource("Development sheet", "xxxxxxxxxxxxxxxxxxxxxxxxxxxxx"),
new GoogleSheetBuildSource("Release sheet", "xxxxxxxxxxxxxxxxxxxxxxxxxxxxx")
};
}
}
Finally, you can use it to build your configs:
public static class UnityGameConfigBuilder
{
const string SharedGameConfigPath = "Assets/StreamingAssets/SharedGameConfig.mpa";
const string StaticGameConfigPath = "Backend/Server/GameConfig/StaticGameConfig.mpa";
// Add path for credentials and configs sheet id
const string GoogleSheetsCredentials = "path/to/Google/credentials";
[MenuItem("Config Builder/Build GameConfig", isValidateFunction: false)]
public static void BuildFullGameConfig()
{
// Configure a config fetcher with the credentials
IGameConfigSourceFetcherConfig fetcherConfig = GameConfigSourceFetcherConfigCore.Create().WithGoogleCredentialsFilePath(GoogleSheetsCredentials);
// Get the game-specific GameConfigBuildIntegration implementation.
GameConfigBuildIntegration integration = IntegrationRegistry.Get<GameConfigBuildIntegration>();
DefaultGameConfigBuildParameters buildParams = new DefaultGameConfigBuildParameters
{
// Get the first source returned by GetAvailableGameConfigBuildSources for DefaultSource.
DefaultSource = integration.GetAvailableGameConfigBuildSources(nameof(GameConfigBuildParameters.DefaultSource)).First();
};
// Build full config (Shared + Server) with the configured sheet and fetcher config
ConfigArchive fullConfigArchive = Task.Run(async () => await StaticFullGameConfigBuilder.BuildArchiveAsync(MetaTime.Now, parentId: MetaGuid.None, parent: null, buildParams, fetcherConfig, new GameConfigBuildDebugOptions { EnableDebugPrints = true })).GetAwaiter().GetResult();
// Extract SharedGameConfig from full config & write to disk
var sharedConfigArchive = ConfigArchive.FromBytes(fullConfigArchive.GetEntryByName("Shared.mpa").Bytes);
Debug.Log($"Writing {SharedGameConfigPath} with {sharedConfigArchive.Entries.Count} entries:\n{string.Join("\n", sharedConfigArchive.Entries.Select(entry => $" {entry.Name} ({entry.Bytes.Length} bytes): {entry.Hash}"))}");
ConfigArchiveBuildUtility.WriteToFile(SharedGameConfigPath, sharedConfigArchive);
// Write full StaticGameConfig to disk
Debug.Log($"Writing {StaticGameConfigPath} with {fullConfigArchive.Entries.Count} entries:\n{string.Join("\n", fullConfigArchive.Entries.Select(entry => $" {entry.Name} ({entry.Bytes.Length} bytes): {entry.Hash}"))}");
ConfigArchiveBuildUtility.WriteToFile(StaticGameConfigPath, fullConfigArchive);
// If in editor, refresh AssetDatabase to make sure Unity sees changed files
AssetDatabase.Refresh();
}
}
Various Metaplay SDK features are configured using the same game config mechanism as your custom config data. As part of integrating a feature, you should enable the configuration of data related to the feature via sheets.
You can customize the config build process for the SDK data libraries in exactly the same fashion as you would for game-specific data.
Here are some examples of SDK features that use game configs:
You can do a lot with your game configs after getting Google Sheets integrated into your project. Here are some suggestions to get you started: