From e33dea7180d859ad6704c7ced59debc7c0ec3eeb Mon Sep 17 00:00:00 2001 From: Astra Date: Fri, 25 Sep 2026 16:00:57 +0100 Subject: [PATCH 1/2] Add release.sh: build, compile Panorama layouts and publish a release Rebuilds from the committed source in the SDK container, compiles the skill card/menu layouts with the CS2 client's resourcecompiler.exe into the jrandomskills_hud Workshop Tools addon, and publishes jRandomSkills-.tar.gz (laid out like game/csgo/) to the git.zio.sh release. Ends by saying whether the compiled layouts changed, i.e. whether Workshop item 3807837213 needs re-uploading - players only get the layouts from the Workshop. Needs FORGEJO_TOKEN in the environment. --- release.sh | 189 +++++++++++++++++++++++++++++++++++++++++++++++++++++ 1 file changed, 189 insertions(+) create mode 100755 release.sh diff --git a/release.sh b/release.sh new file mode 100755 index 0000000..c02fb80 --- /dev/null +++ b/release.sh @@ -0,0 +1,189 @@ +#!/usr/bin/env bash +# Build jRandomSkills and its Panorama layouts, package them as one tarball and publish it as a +# Forgejo release. +# +# ./release.sh e.g. ./release.sh v1.2.4.b2-panorama1 +# +# Commit first: the plugin is rebuilt here from the committed source, so the release always matches +# the tag. The tag is created on HEAD and pushed to origin if it doesn't exist yet. Re-running with +# the same tag replaces that release's attachment. +# +# Asset: jRandomSkills-.tar.gz, laid out like the server's game/csgo/ - extract it there: +# tar -xzf jRandomSkills-.tar.gz -C /srv/cs2/game/csgo +# +# addons/counterstrikesharp/plugins/jRandomSkills/ plugin, deps, languages/, packages/ +# addons/counterstrikesharp/gamedata/ jRandomSkills.gamedata.json +# panorama/{layout,styles}/custom_game/ compiled skill_hud / jrs_menu (.vxml_c/.vcss_c) +# +# No configs/: the plugin writes config.json and skillsInfo.json itself when they are missing, so an +# upgrade never touches the server's config. The Panorama files are compiled from +# "jRandomSkills - SRC Files/panorama" with the CS2 client's resourcecompiler.exe (WSL interop). +# +# Players get the layouts from the Workshop, not from this tarball: the sources are compiled into +# the client's jrandomskills_hud Workshop Tools addon (Workshop item 3807837213, mounted for every +# player by the server's MultiAddonManager, mm_extra_addons). The panorama/ files in the tarball +# only land on the server. When the compiled layouts changed, the script says so at the end: +# re-upload the addon from Workshop Tools. That step stays manual. +set -euo pipefail + +FORGEJO_URL="https://git.zio.sh" +OWNER="cs2" +REPO="jRandomSkills" +# Placeholder - replace, or set FORGEJO_TOKEN in the environment instead. Needs write:repository. +# Only uploading needs it; downloading from the public repo doesn't. Don't commit a real token. +FORGEJO_TOKEN="${FORGEJO_TOKEN:-CHANGE_ME_FORGEJO_TOKEN}" + +# CS2 client used to compile the Panorama layouts, and the Workshop Tools addon compiled into. +CS2_CLIENT_DIR="${CS2_CLIENT_DIR:-/mnt/e/SteamLibrary/steamapps/common/Counter-Strike Global Offensive}" +CS2_ADDON="${CS2_ADDON:-jrandomskills_hud}" +WORKSHOP_ID="3807837213" +PANORAMA_FILES=( + layout/custom_game/skill_hud.xml + layout/custom_game/jrs_menu.xml + styles/custom_game/skill_hud.css + styles/custom_game/jrs_menu.css +) + +# Only these ship from the build output. bin/ also holds CounterStrikeSharp.API.dll, RayTraceApi.dll +# and framework DLLs, which the server already provides and which must not be duplicated per plugin. +PLUGIN_BINARIES=( + jRandomSkills.dll + jRandomSkills.pdb + MaxMind.Db.dll + Newtonsoft.Json.dll + PanoramaManager.dll +) + +TAG="${1:-}" +if [[ -z "$TAG" ]]; then + echo "usage: $0 (e.g. v1.2.4.b2-panorama1)" >&2 + exit 1 +fi +if [[ "$FORGEJO_TOKEN" == "CHANGE_ME_FORGEJO_TOKEN" ]]; then + echo "Set FORGEJO_TOKEN (edit release.sh or export it) first." >&2 + exit 1 +fi + +cd "$(dirname "$(readlink -f "${BASH_SOURCE[0]}")")" + +SRC="jRandomSkills - SRC Files" + +if [[ -n "$(git status --porcelain --untracked-files=no)" ]]; then + echo "Tracked files have uncommitted changes; commit them so the tag matches the release." >&2 + exit 1 +fi + +# --- Build ----------------------------------------------------------------------- +BIN="$SRC/bin/Release/net10.0" +rm -rf "$SRC/bin" "$SRC/obj" +podman run --rm -v "$(pwd)":/src:Z -w "/src/$SRC" \ + mcr.microsoft.com/dotnet/sdk:10.0 dotnet build -c Release + +# --- Stage (layout of game/csgo/) -------------------------------------------------- +OUT="release-out" +STAGE="$OUT/stage" +rm -rf "$OUT" +PLUGIN_DIR="$STAGE/addons/counterstrikesharp/plugins/jRandomSkills" +mkdir -p "$PLUGIN_DIR/languages" "$PLUGIN_DIR/packages" "$STAGE/addons/counterstrikesharp/gamedata" + +for file in "${PLUGIN_BINARIES[@]}"; do + cp "$BIN/$file" "$PLUGIN_DIR/" +done +cp "$SRC"/src/lang/*.json "$PLUGIN_DIR/languages/" +cp -r "$SRC"/packages/. "$PLUGIN_DIR/packages/" +cp "$SRC"/src/gamedata/*.json "$STAGE/addons/counterstrikesharp/gamedata/" + +# --- Panorama: compile sources with the CS2 client --------------------------------- +RC_DIR="$CS2_CLIENT_DIR/game/bin/win64" +[[ -x "$RC_DIR/resourcecompiler.exe" ]] || { echo "resourcecompiler.exe not found in $RC_DIR (set CS2_CLIENT_DIR)." >&2; exit 1; } +CONTENT_ADDON="$CS2_CLIENT_DIR/content/csgo_addons/$CS2_ADDON/panorama" +GAME_ADDON="$CS2_CLIENT_DIR/game/csgo_addons/$CS2_ADDON/panorama" +WIN_CLIENT_DIR="$(wslpath -w "$CS2_CLIENT_DIR")" + +# Checksums of the addon's compiled layouts, to tell whether the Workshop item needs a re-upload. +compiled_sums() { + local file compiled + for file in "${PANORAMA_FILES[@]}"; do + case "$file" in + *.xml) compiled="${file%.xml}.vxml_c" ;; + *.css) compiled="${file%.css}.vcss_c" ;; + esac + if [[ -f "$GAME_ADDON/$compiled" ]]; then + sha256sum "$GAME_ADDON/$compiled" | cut -d' ' -f1 + else + echo "missing $compiled" + fi + done +} +sums_before="$(compiled_sums)" + +for file in "${PANORAMA_FILES[@]}"; do + mkdir -p "$CONTENT_ADDON/$(dirname "$file")" "$STAGE/panorama/$(dirname "$file")" + cp -f "$SRC/panorama/$file" "$CONTENT_ADDON/$file" + + log="$(cd "$RC_DIR" && ./resourcecompiler.exe -game "$WIN_CLIENT_DIR\\game\\csgo" -f \ + -i "$WIN_CLIENT_DIR\\content\\csgo_addons\\$CS2_ADDON\\panorama\\${file//\//\\}" 2>&1 | tr -d '\r')" + if ! grep -q 'OK: 1 compiled, 0 failed' <<<"$log"; then + echo "$log" >&2 + echo "Failed to compile $file" >&2 + exit 1 + fi + + case "$file" in + *.xml) compiled="${file%.xml}.vxml_c" ;; + *.css) compiled="${file%.css}.vcss_c" ;; + esac + cp -f "$GAME_ADDON/$compiled" "$STAGE/panorama/$compiled" + echo "Compiled $compiled" +done + +# --- Package ------------------------------------------------------------------------- +TARBALL="jRandomSkills-${TAG}.tar.gz" +tar -czf "$OUT/$TARBALL" -C "$STAGE" addons panorama +rm -rf "$STAGE" + +echo "Packaged $OUT/$TARBALL:" +tar -tzf "$OUT/$TARBALL" | grep -v '/$' + +# --- Tag ------------------------------------------------------------------------- +if ! git rev-parse -q --verify "refs/tags/$TAG" >/dev/null; then + git tag -a "$TAG" -m "$TAG" +fi +git push origin "refs/tags/$TAG" + +# --- Release --------------------------------------------------------------------- +API="$FORGEJO_URL/api/v1/repos/$OWNER/$REPO" +AUTH=(-H "Authorization: token $FORGEJO_TOKEN") + +release_json="$(curl -fsS "${AUTH[@]}" "$API/releases/tags/$TAG" 2>/dev/null || true)" +if [[ -z "$release_json" ]]; then + body="$(git log -1 --format=%B "$TAG")" + release_json="$(jq -n --arg tag "$TAG" --arg body "$body" \ + '{tag_name: $tag, name: $tag, body: $body, draft: false, prerelease: false}' | + curl -fsS "${AUTH[@]}" -H "Content-Type: application/json" -X POST --data @- "$API/releases")" + echo "Created release $TAG" +else + echo "Release $TAG already exists, replacing its attachment" +fi +release_id="$(jq -r '.id' <<<"$release_json")" + +existing_id="$(jq -r --arg n "$TARBALL" '.assets[]? | select(.name == $n) | .id' <<<"$release_json")" +if [[ -n "$existing_id" ]]; then + curl -fsS "${AUTH[@]}" -X DELETE "$API/releases/$release_id/assets/$existing_id" >/dev/null +fi +curl -fsS "${AUTH[@]}" -X POST -F "attachment=@$OUT/$TARBALL" \ + "$API/releases/$release_id/assets?name=$TARBALL" >/dev/null +echo "Uploaded $TARBALL" + +echo +echo "Download: $FORGEJO_URL/$OWNER/$REPO/releases/download/$TAG/$TARBALL" +echo "Install: tar -xzf $TARBALL -C /srv/cs2/game/csgo" + +echo +if [[ "$(compiled_sums)" != "$sums_before" ]]; then + echo "Workshop: the compiled Panorama layouts CHANGED. Players won't see the change until the" + echo " '$CS2_ADDON' addon is re-uploaded from Workshop Tools to item $WORKSHOP_ID:" + echo " https://steamcommunity.com/sharedfiles/filedetails/?id=$WORKSHOP_ID" +else + echo "Workshop: compiled Panorama layouts unchanged; no Workshop update needed." +fi From 5d0cf7ce80841056a56c325ad8e786899e7196c9 Mon Sep 17 00:00:00 2001 From: Astra Date: Sun, 27 Sep 2026 18:16:48 +0100 Subject: [PATCH 2/2] Build against CounterStrikeSharp 1.0.376 --- jRandomSkills - SRC Files/jRandomSkills.csproj | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/jRandomSkills - SRC Files/jRandomSkills.csproj b/jRandomSkills - SRC Files/jRandomSkills.csproj index d9991af..b553bd8 100644 --- a/jRandomSkills - SRC Files/jRandomSkills.csproj +++ b/jRandomSkills - SRC Files/jRandomSkills.csproj @@ -21,7 +21,7 @@ - +