Contributing: Creating a New Generator
This page is the end-to-end recipe for adding a new data-driven generator in kore.
The examples below use a fictional custom_reward resource so the shape stays easy to transpose to real Minecraft schemas.
1) Start from the closest existing feature
Before creating files, pick the nearest generator already in Kore and mirror its structure.
Good references, in alphabetical order:
What you want to mirror:
DataPackregistration.DataPackextension function.Generatorinheritance and path behavior.- Package layout.
- Test shape.
If the feature needs a brand-new registry argument type, add it through the generation pipeline first. Do not hand-edit kore/src/main/generated or build/generated/....
2) Create the feature class
Place the feature in the matching package under kore/src/main/kotlin/io/github/ayfri/kore/features/....
Checklist for the class itself:
- Extend
Generatorwith the correctresourceFolder. - Keep
generateJson(dataPack)thin and delegate to the shared encoder when the structure is straightforward. - Mark
fileNameas@Transient. - Make the feature
@Serializable. - Only override
getPathFromDataDir(...)when the resource path is genuinely special.
3) Register the generator in DataPack
Add the new list in DataPack.kt, in alphabetical order with the other registered generators.
This is what makes the feature participate in the normal datapack generation lifecycle.
4) Add the DataPack extension function
The extension function is the public builder entry point.
Keep it consistent with the rest of Kore:
- Add the instance to the registered list.
- Apply
initlast. - Instantiate the feature once.
- Return the matching typed argument.
If the resource can be referenced by tags, preserve the corresponding *OrTagArgument pattern as well.
5) Reuse serializers and argument types
Before adding custom serialization logic, check Contributing: Architecture and Patterns.
In practice, the decision order is:
- Reuse an existing serializer.
- Reshape the model if that makes an existing serializer work.
- Add a new serializer only when the first two options fail.
This keeps JSON output aligned with the rest of Kore instead of creating one-off conventions.
6) Add tests immediately
Generator changes in kore should ship with targeted tests under kore/src/test/kotlin/io/github/ayfri/kore.
For a simple resource, the test usually follows this shape:
At minimum, validate:
- Edge cases or regressions specific to the feature.
- The emitted JSON shape.
- The generated file path.
7) Update documentation in the same PR
Every user-visible feature needs docs under website/src/jsMain/resources/markdown/doc.
Typical documentation work includes:
- A contributor note when the implementation pattern is non-obvious.
- A user-facing usage page when the feature becomes public API.
- Updated links from entry pages when navigation changes.
For page placement, routing, and required frontmatter keys, reuse the documentation contract described in Contributing: Architecture and Patterns.
8) Validate before opening the PR
For kore changes, the baseline check is:
Before opening the PR, verify that:
DataPackregistration remains alphabetically ordered.- Docs reflect the final API shape.
- No generated file was hand-edited.
- Tests cover the feature.
9) Done checklist
You are usually done when the feature includes all of the following:
- A
DataPackextension function returning the typed argument. - A
DataPackregistration entry. - A
Generatorsubclass with the correct path behavior. - Documentation updates in
website/.../markdown/doc. - Tests in
kore/src/test.
