Documentation site for the "Assorted" Minecraft mod series by Grim3212, published at assortedmods.com.
Built with Nuxt 4 and prerendered to static files.
Needs Node 26, pinned in .nvmrc (nvm use if you use nvm). CI reads the same file, and
@types/node follows the same major.
yarn installRuns on http://localhost:3000:
yarn devyarn generate # static site into .output/public
yarn preview # serve the built site locally
yarn lintEach family (Assorted Tech and so on) has a page at /<family>, and each of its mods has its own
page at /<family>/<mod> built on the PartPage component. The list of families and mods, their
names, descriptions, download pages and logos come from the mod repos:
yarn mods # regenerate app/data/mods.json and public/logos
yarn mods --check # only report what is missingIt reads each repo's root gradle.properties (family_name, assorted_mods) and every mod's own
gradle.properties (mod_name, mod_description, curseforge_slug, modrinth_id). Assorted Lib is
read the same way from ../AssortedLib but is not a family. It has its own page at /lib, last in the
sidebar and left off the landing page, where the config every mod shares is listed. A download link
shows as "soon" until the mod has that id. scripts/mods/overrides.json holds what gradle.properties
does not, like a nicer Modrinth slug or a family with no bundle. Rerun it when a mod gets its store
pages or a new logo. When a page moves, add the old path to redirects.json so links keep working.
The pictures on a mod's page are the same ones as on its CurseForge and Modrinth pages. They live
in public/gallery/<family>/<dir> with their captions in app/data/gallery.json, and a script
outside this repo copies them in from the photo shoots, so they are not edited here. A page shows
its main clip under the header and places the shots next to the text they go with:
<GalleryShot name="pyramid" /> <!-- 4-pyramid.webp, named without its number -->
<GalleryClip name="breaking" /> <!-- clip-breaking.webp; the main clip.webp is already at the top -->Any shot or extra clip a page does not place is shown in the Gallery at the end, and clicking any shot opens the lightbox over all of them. A name that does not exist fails the build. A bundle's gallery is its parts' first shots, so a family page shows the "everything" shot and the part cards carry the rest.
Pictures that are not in a gallery, like a screen or a tooltip, are in public/figures/<family>
and go on a page with <PageFigure src="/figures/tech/sensor-range.webp" caption="..." />.
Recipes on the pages are <Recipe id="assortedmachines:machine_core" /> components. They read
app/data/recipes/<namespace>/<path>.json and the item icons in public/icons, both generated
from the mods' datagen output and icon exports by:
yarn recipes # regenerate app/data/recipes and public/icons
yarn recipes --check # only report what would change and any problemsThe script scans the pages for every <Recipe id>, reads the recipe from each mod in the sibling
repos (../Assorted*/mods/*/common/src/generated/server), resolves tags and names, and copies the
icons out of the mods' icon exports. The icons are rendered by the game itself: in a mod
checkout,
./gradlew :all:neoforge:runExportIcons(or :<mod>:neoforge:runExportIcons for a single mod)
starts the client with the IconExporter from AssortedLib armed, which joins a throwaway flat
world, draws every loaded item the way the inventory does (models, block entity renderers,
tints, lighting) into the repo's build/icons and quits. Rerun it in a mod whenever its models
or textures change, then yarn recipes. Items whose icon depends on components (the coloured
sidings) are listed in scripts/recipes/icon-stacks.json, which yarn recipes maintains and the
export runs read, so a new variant takes one more export run after the page referencing it is
added. The recipe backgrounds in public/icons/gui are the real container GUI textures
(crafting table, furnaces, stonecutter, smithing table, grinding mill, alloy forge) cropped to
the recipe area, with the slot positions written to app/data/gui.json;
scripts/recipes/gui.mjs is where a new station gets added. It needs the mod repos next to this
one and the Minecraft client jar plus NeoForge jar from the gradle cache (built once by any mod
build). scripts/recipes/config.mjs lists the environment variables that override those
locations. Special recipe types the game does not describe in JSON (bag dyeing, locking an
ender chest) live in scripts/recipes/extra, and a PNG dropped into
scripts/recipes/icon-overrides/<namespace>/<item>.png replaces an exported icon.
Both outputs are committed, so a deploy does not need the mods or the game.
Deployed to AWS with CDK. Pushes to main publish automatically, and the Deploy workflow can also be run from the Actions tab.