Files
rivencraft/docs/PUBLISHING_APIS.md
T
2026-10-31 20:46:41 -04:00

83 lines
4.0 KiB
Markdown

# Publishing Rivencraft with the Gitea, Modrinth, and CurseForge APIs
The local helper is [`scripts/publish_mod_sites.py`](../scripts/publish_mod_sites.py).
It previews a release unless `--publish` is explicitly supplied. The current
configuration is for the Minecraft **26.3** artifact only. The 1.21.1 line needs
its required external dependencies mapped on both sites before API publishing
is enabled for it.
## One-time token setup
For Gitea, an existing personal access token is sufficient if it has
`write:repository` scope. That scope covers release creation and attachment
upload; do not grant `all` if a narrower token is available. Create or inspect
tokens under [Gitea user settings → Applications](https://git.paddedcell.org/user/settings/applications).
The helper checks token identity and scope without displaying the secret.
Create a [Modrinth personal access token](https://docs.modrinth.com/api/#authentication)
in account settings with `VERSION_CREATE` (upload) and `USER_READ` (read-only
credential check) scopes. Create a
[CurseForge Upload API token](https://support.curseforge.com/support/solutions/articles/9000197321)
from the author's API Tokens page. Treat both as passwords: never put them in
git, chat, a release note, or a command-line argument.
In a terminal at the repository root, run these one at a time and paste the
corresponding token into the hidden prompt:
```sh
python3 scripts/publish_mod_sites.py store-token modrinth
python3 scripts/publish_mod_sites.py store-token curseforge
python3 scripts/publish_mod_sites.py store-token gitea
```
The tokens are stored in the desktop Secret Service keyring under
`application=rivencraft-publishing`, separately by site. The script also accepts
`RIVENCRAFT_MODRINTH_TOKEN` or `RIVENCRAFT_CURSEFORGE_TOKEN` environment variables,
but these take precedence over keyring entries and should not be put in shell
history or startup files.
Verify the credentials without uploading anything:
```sh
python3 scripts/publish_mod_sites.py check-token modrinth
python3 scripts/publish_mod_sites.py check-token curseforge
python3 scripts/publish_mod_sites.py check-token gitea
```
## Release workflow
Build the JAR, write a Markdown changelog, and preview the metadata:
```sh
python3 scripts/publish_mod_sites.py release \
--jar ports/mc263/build/libs/rivencraft-26.3-1.0.1.32-beta.1.jar \
--changelog ports/mc263/RELEASE_NOTES_1.0.1.32-beta.1.md \
--version 1.0.1.32-beta.1 \
--name 'Rivencraft 1.0.1.32-beta.1 — NeoForge 26.3' \
--minecraft 26.3 --java 25 --channel beta
```
For a *new* version only, append `--publish` to upload to both sites. Use
`--site modrinth` or `--site curseforge` to target one site. Modrinth rejects an
existing version number; CurseForge may not, so check its file list before any
retry after a partial failure. CurseForge approval may take additional time.
The default destination is now all three sites. The Gitea release step requires
the annotated version tag to have been pushed first. Gitea's `Vx.y.z.b-mc26.3-beta.1`
tag convention is derived from the version and channel; an existing release
with different title or notes is never overwritten. If release creation
succeeds but its JAR upload fails, rerun with `--site gitea --publish` to resume
only the missing attachment. `--site both` retains the earlier Modrinth and
CurseForge-only behavior.
The helper uses Gitea's documented
[`POST /repos/{owner}/{repo}/releases`](https://docs.gitea.com/api/operations/repo-create-release/)
and [release attachment endpoint](https://docs.gitea.com/api/operations/repo-create-release-attachment/),
plus Modrinth's documented multipart
[`POST /version`](https://docs.modrinth.com/api/operations/createversion/) and
CurseForge's documented
[`POST /api/projects/{projectId}/upload-file`](https://support.curseforge.com/support/solutions/articles/9000197321)
with the JAR, changelog, version channel, NeoForge, Minecraft version, Java
version, and client/server environment. It sets no external dependencies for
26.3, which uses Rivencraft's first-party Age backend.