What a sync writes
Every file a sync produces, which of them land in your Unreal project, which ship in a build, and what belongs in version control.
All documentation — The plugin and sync
Start here
Concepts
Authoring for a build
Playing a story
The generated assets and code
The plugin and sync
On this page
A sync runs in two stages, and they leave files in two different places. Knowing which is which answers most of the questions that come up afterwards — what to commit, what to ignore, what is safe to delete, and what a teammate needs on their machine.
Stage one — the sync output directory
TaleShardSync writes a directory of its own, under Saved/TaleShard/ in your project. You never
need to open it, and nothing in it belongs in your Content. It is listed here because the sync
report names these files, and because a diagnostic that mentions one is easier to read if you know
what it is.
| File | What it is |
|---|---|
runtime.json | The resolved story — every board, node, field value and expression. This is what your game plays from. |
codegen.json | The resolved declarations — entity definitions, traits, option sets, variables, commands, tables, media, tags and every translation. This is what the generator builds your assets and types from. |
manifest.json | The project’s name, slug and export-format version. |
media-map.json | Filename to media id, for the files in media/. |
media/ | The media files themselves, in the folder layout the editor shows. |
sync-result.json | The run’s own report: what changed, what was downloaded, what was skipped. |
board-delta.json | Only on a board-only sync — what changed in that pass. |
The directory is rebuilt from scratch on every sync, so nothing in it survives and nothing in it is worth editing.
Stage two — what lands in your project
The plugin reads that directory and writes into your project. This is the half you version-control.
| Path | What it is | Regenerated |
|---|---|---|
Content/TaleShard/Generated/ | the payload asset, the entity stores and index, the enum, command, variable, board, node-type and media indexes, the string tables, the manifest — the data layer | every sync |
Content/TaleShard/Media/ | your media, imported as textures and sounds | every sync that changed media |
Config/Tags/TaleShardGenerated.ini | one gameplay tag per code in the project | every sync |
Source/<YourModule>/TaleShardGenerated/ | the typed C++ — the typed layer. Only when C++ is generated, and only when the schema changed | a schema change |
Source/<YourModule>/<YourModule>.Build.cs | one edit, only when C++ is generated: the plugin’s modules added to the dependency list when they are missing. It is one of the two files a sync edits without owning them, with Config/DefaultGame.ini below, and the sync window says when it does | the first generation that finds one missing |
Config/DefaultGame.ini | one +PrimaryAssetTypesToScan= line for each generated asset type that is missing under Project Settings > Asset Manager, or that does not yet scan the content root, so a packaged game finds them. Nothing else in the file changes, and the lines you or another plugin wrote stay as they were. The plugin’s own /TaleShard/Widgets folder, which holds the default dialogue screen, is always cooked by the plugin’s Config/Game.ini, so nothing is written for it | the first sync that finds a type missing, and the first after the content root changes |
Saved/TaleShard/ | per-machine sync state: the cached document, the replication cursor, the media sync state and the manifest of what the last run generated | every sync |
The content root and the generated source folder are yours to configure in Project Settings → Plugins → TaleShard; the folders the plugin writes into are not yours to write in. Every sync sweeps what it no longer produces from the folders it owns — and only what its own manifest recorded, so a file it did not write is never touched.
What ships in a build
The payload asset and everything under Content/TaleShard/ ship: the game reads them at play
time. The generated C++ is compiled into your module like any other source.
codegen.json never ships. It is an input to generation and stays under Saved/ — there is nothing
to exclude, because it never reaches your Content in the first place.
What to commit
Commit the generated assets, the tag ini and the generated C++. They are build inputs like any other: a teammate who clones the project should be able to open it and play without running a sync first, and a build machine should never need an API key.
Two things follow from that, and they surprise people:
- A generated file is overwritten, never merged. Never hand-edit one — see the three files for the single deliberate exception. If two people sync at different times you will see diffs in generated assets; that is expected, and the generator is deterministic, so the same project always produces the same output.
Saved/is per-machine. It holds a replication cursor and a cached copy of the document. Committing it is harmless but pointless, and a stale one on someone else’s machine simply causes one full sync. The sync tool ships inside the plugin’s release zip — see the requirements.
Importing a sync output without the sync tool
A folder the sync tool wrote — runtime.json, codegen.json and the media — can be imported into a
project with no server, no API key and no sync tool:
UnrealEditor-Cmd <project> -run=TaleShardImport -from=<sync output directory>It does what a full sync does after its download: the payload asset, the media and every generated
asset. The folder is copied, never modified. It exits 0 when the import and the generation both
succeeded and 1 otherwise, with every diagnostic in the log — the entry point for a build machine
or a test run. From C++ the same import is FTaleShardSyncService::ImportFromDirectory.
A node whose type the project does not define is reported as a warning; it does not stop the
import. The node still ships in the payload, and when a playthrough reaches it the engine reports an
unsupported-node-type error and carries on through the node’s first exit, or ends the path when
it has none.
When something looks wrong
The sync report names what it could not do rather than failing silently, and both payloads carry
their own diagnostics, which the plugin replays into the Output Log. An asset that is missing from
Content/TaleShard/ after a sync has almost always been reported — read the log before re-running.
Two failures are refusals rather than bugs, and both name their own fix:
- A payload the plugin does not understand. The sync tool and the plugin come from one release; if you update one without the other, the reader refuses the file rather than generating half a project from it, and a sync refuses to start when their major versions differ.
- A C++ generation that does not validate. Nothing is written; the previous generation stands, and the report says which rule the emitted code broke.
When only the C++ could not be written — no module to compile it, or a Build.cs the sync could
not add the plugin’s modules to — the sync window reads Synced — C++ not generated and gives
the reason: the assets and the story are written, and play. The codes are in
diagnostics.