Choose structure instance IDs
When to use
Choose an ID strategy when placed structures must retain identity across actions, saves, replays, network messages, or project-owned game objects. A structure definition ID identifies a reusable type; a structure instance ID identifies one placement. The instance ID provider is only the fallback that creates that value when the request does not supply one.
Before you start
Decide whether the caller already owns a stable identity. Pass that ID explicitly whenever it is part of saved or networked game state. An ID provider is used only when placement omits the ID.
Procedure
| Strategy | Choose it when |
|---|---|
| Explicit instance ID | A save record, entity, or command already owns the identity. |
| GridDeterministicStructureInstanceIdProvider | Replays, tests, or synchronized simulations need reproducible generated IDs. |
| GridGuidStructureInstanceIdProvider | Placements need globally unique IDs and reproducibility is not required. |
| Project implementation of IGridStructureInstanceIdProvider | Identity follows a save, network, or domain naming convention. |
Custom providers run while an action plan is built. Read only the supplied planning context, return
a non-empty ID that is absent from ExistingInstanceIds, and do not mutate the board or external
state. When a preferred project ID already exists, choose the next available suffix
deterministically so repeated previews produce the same plan.
Excerpt — generate a collision-free deterministic instance ID. Tested using public APIs.
public sealed class DocumentationStructureInstanceIdProvider :
IGridStructureInstanceIdProvider
{
private readonly string prefix;
public DocumentationStructureInstanceIdProvider(string prefix)
{
this.prefix = string.IsNullOrWhiteSpace(prefix)
? throw new ArgumentException("An ID prefix is required.", nameof(prefix))
: prefix.Trim();
}
public string CreateId(GridStructureInstanceIdContext context)
{
if (context == null)
throw new ArgumentNullException(nameof(context));
string preferred =
$"{prefix}.{context.DefinitionId}.r{context.SourceRevision + 1:D6}.p{context.PlacementOrdinal:D3}";
HashSet<string> existing = new(
context.ExistingInstanceIds,
StringComparer.Ordinal);
if (!existing.Contains(preferred))
return preferred;
for (int suffix = 1; suffix < int.MaxValue; suffix++)
{
string candidate = $"{preferred}.{suffix:D3}";
if (!existing.Contains(candidate))
return candidate;
}
throw new InvalidOperationException("No unique structure instance ID is available.");
}
}
For an authored project, assign the provider to the runtime defaults asset or the relevant board override, then generate runtime settings. For a code-owned board, include it in the GridRuntimeConfiguration supplied when the state is built.
Result
Every placed instance has a non-empty identity from the explicit request or the configured provider. Preview and Apply plan against the same identity rules, while applying an action performs fresh planning against current state.
Troubleshooting
| Symptom | Check |
|---|---|
| Replays produce different IDs | Use the deterministic provider and keep its seed inputs stable. |
| Restore cannot match a structure | Preserve the saved instance ID rather than generating a replacement during restore. |
| A custom provider duplicates an ID | Check ExistingInstanceIds and add a deterministic suffix, or use an explicit project-owned ID. |