Skip to content

Rubric Concepts

Oliver Yasuna edited this page Jul 3, 2026 · 2 revisions

Rubric — Concepts

Vocabulary you'll see across Rubric's Javadoc, error messages, and this wiki.

Config, Schema, Entry, Category

  • Config — the annotated class (or ConfigSpec for builder-defined configs). One @Config type maps to one on-disk file.
  • Schema — the immutable in-memory description of a config: id, name, format, version, and a tree of SchemaCategory / SchemaEntry. Built once at registration time.
  • SchemaCategory — a named, ordered group of entries and sub-categories. Comes from an @Category annotation, or implicitly from a nested class field.
  • SchemaEntry — one leaf value: key, type, default, metadata, and how to read/write it on the config instance. Every top-level @Config field that isn't a nested object becomes one.

The full type graph lives in the com.oliveryasuna.mc.rubric.schema package.

Format, ValueTree, ValueNode

  • Format — enum TOML / JSON / JSON5. Chosen by @Config#format.
  • ValueTree — Rubric's format-neutral parsed representation. Every format adapter parses to a ValueTree, and Rubric writes back through the adapter that matches the schema's format.
  • ValueNode — sealed base type; concrete kinds:
    • Section — an ordered map of child nodes (a TOML table, a JSON object).
    • ListNode — an ordered sequence of nodes.
    • Scalar — a leaf (String, Boolean, Number, or null).

Consumers rarely touch ValueTree directly. It shows up in custom format adapters and codec extension points.

ValueCodec, CodecRegistry

  • ValueCodec<T> — encodes a Java T into a ValueNode and decodes back. Built-in codecs handle primitives, String, enums, List, Map, and a small set of scalars (UUID, Instant, Duration). Register your own via CodecRegistry.registerCustom(Class, ValueCodec) for types that don't fit the defaults — see also Formats for the Mojang Codec<T> bridge.
  • CodecRegistry — resolves the right codec for a ValueType. Threaded into the schema reader so registered leaf types (e.g. ResourceLocation) are classified as scalars instead of recursed into as nested categories.

ConfigManager, ConfigHandle, ConfigValue

  • ConfigManager<S> — internal runtime for one config. Owns the POJO instance, the current snapshot, the event bus, and the reload pipeline. You usually get one indirectly via Rubric.register(...).
  • ConfigHandle<T> — the public wrapper you keep a reference to. handle.get() returns the current POJO, handle.manager() exposes the manager for events / reload listeners / etc.
  • ConfigValue<V> — typed view of one entry by dotted path. Reads the current snapshot, subscribes to changes for its path. Optional; convenient when you only care about a single value.

Snapshot, Correction, LoadResult

  • ConfigSnapshot — immutable dotted-path view of every value at a moment in time. The manager swaps snapshots atomically on reload.
  • Correction — a single value that was reset during load (invalid, out of range, mismatch with @OneOf, etc.). Details in Validation.
  • LoadResult — what a load() returns: the resulting snapshot, the list of corrections, and (if any) the migration report.

Reload tier, Sync scope, Origin

Three orthogonal quanta attached to every entry:

  • Reload tierLIVE (apply immediately), WORLD (next world load, the default), RESTART (game restart required). Set via @Reload or the shortcut @RequiresRestart. Consumed by the GUI to decide whether to prompt for a restart, and by ReloadController when diffing snapshots.
  • Sync scopeCLIENT (local only, the default), SERVER (server-authoritative), COMMON (server-authoritative when connected, local in singleplayer). Set via @Sync. Consumed by SyncService — see Sync.
  • Origin — provenance tag for one path. DEFAULT (never touched), LOCAL_EDIT (set by local action, loaded from disk, or a server-accepted ClientEdit), FROM_REMOTE (applied from a server snapshot). save() excludes FROM_REMOTE entries so the local file never gets polluted with server-authoritative values.

Migration

  • Migrator — reads and writes the schema version from a reserved root key, runs registered steps between versions.
  • MigrationStep — an ordered set of MigrationOps that upgrades the tree to a specific target version.
  • MigrationOp — a single in-place transform on a Section. Factories in MigrationOps cover renaming, moving, and mapping values. See Migration.

Validator, Validation

  • Validator<T> — validates one value; may return a suggested corrected replacement.
  • ValidationResult — either ok() or invalid(...) with a list of ValidationIssues.
  • Corrector — runs entry validators over a populated instance, applying the first suggested correction (or the entry's default) on failure. Never throws on bad data.

Sync

  • SyncService — per-role (server or client) orchestrator. Handshakes, pushes snapshots, applies deltas, forwards client edits.
  • ScopeEnforcer — filters a config by Sync.Scope — extracts what the server should push, applies only the scoped entries on the client.
  • NetworkTransport — loader-agnostic SPI. The Fabric integration ships FabricNetworkTransport; the NeoForge integration ships NeoForgeNetworkTransport.
  • PermissionGate — server-side authorization for client-edit packets.

Platform SPI

  • Platform — loader-supplied services the loader-neutral core needs: config directory, main-thread executor, logger. Rubric's Fabric integration ships FabricPlatform; the NeoForge integration ships NeoForgePlatform. You don't implement this unless you're porting to a new loader.

Where next

Every one of these has its own reference page:

Clone this wiki locally