Skip to content

Building from Source

Brennan Hatton edited this page Jun 10, 2026 · 1 revision

Building from Source

Adventure Item Stats is an Architectury project that builds three loader jars (Fabric, Forge, NeoForge) from one shared codebase.

Prerequisites

  • JDK 21 — required. The Fabric mixin transformer for 1.21.1 can't read class files from JDK 23+, so the toolchain is pinned to 21. Gradle will provision a JDK 21 automatically if you don't have one.
  • Git
  • No global Gradle install needed — use the bundled ./gradlew wrapper.
git clone https://github.com/bh679/adventureitemstats-mc.git
cd adventureitemstats-mc

Project layout

Module What's in it
common/ All the real logic — loader-agnostic. The StatsModifier API, the StatsRoller math, the LootTableMixin, and the JUnit tests.
fabric/ Fabric entry point + fabric.mod.json.
forge/ Forge entry point + META-INF/mods.toml.
neoforge/ NeoForge entry point + META-INF/neoforge.mods.toml.

Each loader module is a thin shell that bundles common/. Almost all changes happen in common/.

Key versions live in gradle.properties: minecraft_version, mod_version, and the pinned fabric_*, forge_version, and neoforge_version lines.

Build

./gradlew build          # compile + package all three loader jars

Output jars land in each module's build/libs/:

fabric/build/libs/adventureitemstats-fabric-<version>.jar
forge/build/libs/adventureitemstats-forge-<version>.jar
neoforge/build/libs/adventureitemstats-neoforge-<version>.jar

(Ignore the -sources and -dev/-dev-shadow classified jars — the production jar is the unclassified one.)

Run a dev client

./gradlew fabric:runClient      # Fabric dev client
./gradlew neoforge:runClient    # NeoForge dev client
./gradlew forge:runClient       # ⚠ see caveat below

Forge dev-client caveat

forge:runClient is currently blocked by an upstream JPMS module conflict between Architectury Loom 1.13 and Forge 1.21.1 (architectury-loom#284). This is a dev-environment-only problem — the Forge production jar builds and runs fine. Verify Forge by loading the built jar in a real Forge install (load → creative inventory → roll a loot chest) rather than via runClient.

If a dev client hangs, stop the Gradle daemon:

./gradlew --stop

Tests

The math in StatsRoller is pure and unit-tested with JUnit. The suite lives in common/:

./gradlew :common:test

It covers the clamp bounds, the identity (zero-Gaussian) roll, the quality and tradeoff axes for both weapons and armor, a 10,000-sample stress test that every factor stays within [0.5, 1.5], and that skip-flags consume no RNG entropy.

Cross-loader parity

Any change touching the loot mixin, the StatsModifier API, the attribute-modifier logic, or the distribution parameters must be verified on Fabric and NeoForge dev clients, with a Forge production-jar smoke test (per the caveat above). Rolled-item behavior should be identical across all three loaders since the logic all lives in common/.

Releasing

Releases are automated and dispatch-only — see Contributing and the in-repo docs/PUBLISHING.md. Do not create git tags by hand; the release workflow is the source of tags.

Clone this wiki locally