A RuneTek3 client (377) that is deobfuscated, converted to Kotlin, and includes QoL improvements.
0

Configure Feed

Select the types of activity you want to include in your feed.

1stages: 2 - build 3 - publish 4 5variables: 6 GRADLE_OPTS: "-Dorg.gradle.daemon=false" 7 PACKAGE_NAME: "hla-client" 8 JAR_NAME: "377.jar" 9 # Server connection defaults (same across regions) 10 GAME_PORT: "43594" 11 ONDEMAND_PORT: "43594" 12 JAGGRAB_PORT: "43595" 13 HTTP_PORT: "8080" 14 RSA_PUB: "65537" 15 16# Per-region build. Each matrix row produces hla-<REGION>-client.zip with the 17# correct server host + RSA modulus baked into config/client-config.yaml. 18# 19# CI/CD variables required (set in Settings → CI/CD → Variables, regular type): 20# HLA_HOST_USE # e.g. use.objects.pw 21# HLA_HOST_USW # e.g. usw.objects.pw 22# HLA_RSA_MODULUS_USE # decimal modulus from rsa.yml on use.objects.pw 23# HLA_RSA_MODULUS_USW # decimal modulus from rsa.yml on usw.objects.pw 24# 25# To add a region: append a row to the matrix below and add HLA_HOST_<X> + 26# HLA_RSA_MODULUS_<X> variables. Modulus values are public (anyone connecting 27# sees them) so they don't need to be masked. 28build: 29 stage: build 30 image: eclipse-temurin:21-jdk-alpine 31 tags: 32 - docker 33 parallel: 34 matrix: 35 - REGION: "us-east" 36 - REGION: "us-west" 37 before_script: 38 - apk add --no-cache zip 39 - chmod +x gradlew 40 script: 41 # Resolve region-specific values from CI variables 42 - | 43 case "$REGION" in 44 us-east) 45 HOST="${HLA_HOST_USE:?HLA_HOST_USE not set in CI vars}" 46 MODULUS="${HLA_RSA_MODULUS_USE:?HLA_RSA_MODULUS_USE not set in CI vars}" 47 ;; 48 us-west) 49 HOST="${HLA_HOST_USW:?HLA_HOST_USW not set in CI vars}" 50 MODULUS="${HLA_RSA_MODULUS_USW:?HLA_RSA_MODULUS_USW not set in CI vars}" 51 ;; 52 *) 53 echo "Unknown region: $REGION" >&2 54 exit 1 55 ;; 56 esac 57 export HOST MODULUS 58 59 - export ZIP_NAME="hla-${REGION}-client.zip" 60 - echo "Building ${ZIP_NAME} for ${HOST} (modulus ${MODULUS:0:16}…)" 61 62 # Build the fat jar (same for all regions) 63 - ./gradlew clean jar 64 65 # Stage the dist directory 66 - mkdir -p dist/config 67 - cp build/libs/${JAR_NAME} dist/ 68 69 # Generate region-specific client-config.yaml 70 - | 71 cat > dist/config/client-config.yaml <<EOF 72 # Generated by CI for region: ${REGION} 73 # Server: ${HOST} 74 # Build: ${CI_COMMIT_SHORT_SHA} 75 net: 76 address: ${HOST} 77 game_port: ${GAME_PORT} 78 ondemand_port: ${ONDEMAND_PORT} 79 jaggrab_port: ${JAGGRAB_PORT} 80 http_port: ${HTTP_PORT} 81 cache: 82 cacheDir: ./.377 83 jaggrabEnabled: true 84 rsa: 85 rsaEnabled: true 86 rsaPub: ${RSA_PUB} 87 rsaModulus: ${MODULUS} 88 login: 89 useStaticCredentials: false 90 username: "" 91 password: "" 92 game: 93 roofsEnabled: true 94 freeTeleports: false 95 debugContext: false 96 EOF 97 98 # Launchers (matches the previous CI's behavior) 99 - echo '#!/bin/sh' > dist/run.sh 100 - echo 'cd "$(dirname "$0")" && java -jar 377.jar' >> dist/run.sh 101 - chmod +x dist/run.sh 102 - cp dist/run.sh dist/run.command 103 - chmod +x dist/run.command 104 - printf '@echo off\r\ncd /d "%%~dp0"\r\njava -jar 377.jar\r\npause\r\n' > dist/run.bat 105 106 # Bundle 107 - cd dist && zip -r "../${ZIP_NAME}" ${JAR_NAME} config/ run.sh run.command run.bat 108 artifacts: 109 paths: 110 - "hla-${REGION}-client.zip" 111 expire_in: 90 days 112 cache: 113 key: 114 files: 115 - build.gradle 116 paths: 117 - .gradle/ 118 119publish: 120 stage: publish 121 image: alpine:latest 122 tags: 123 - docker 124 parallel: 125 matrix: 126 - REGION: "us-east" 127 - REGION: "us-west" 128 # Both build and publish use identical parallel:matrix definitions, so GitLab 129 # auto-pairs them. Listing `job: build` without an explicit matrix downloads 130 # all parallel build artifacts (a few MB of waste — negligible). Each publish 131 # job uses its own REGION to pick its zip from the bundle. 132 needs: 133 - job: build 134 artifacts: true 135 rules: 136 - if: $CI_COMMIT_BRANCH == "main" 137 before_script: 138 - apk add --no-cache curl jq 139 # GitLab generic packages append on duplicate uploads (every push leaves an 140 # extra copy in the registry). Workflow: find any existing files in 141 # ${PACKAGE_NAME}/latest matching this region's zip name, DELETE them, then 142 # upload fresh. Each parallel job only touches its own ZIP_NAME so the two 143 # regions don't race. 144 script: 145 - export ZIP_NAME="hla-${REGION}-client.zip" 146 - echo "Publishing ${ZIP_NAME} @ ${CI_COMMIT_SHORT_SHA}" 147 148 # Find package id for hla-client/latest (empty string if first publish) 149 - | 150 PACKAGE_ID=$(curl --silent --fail --header "JOB-TOKEN: ${CI_JOB_TOKEN}" \ 151 "${CI_API_V4_URL}/projects/${CI_PROJECT_ID}/packages?package_name=${PACKAGE_NAME}&package_version=latest" \ 152 | jq -r '.[0].id // empty') 153 echo "Existing package id: '${PACKAGE_ID:-<none>}'" 154 155 # Delete prior copies of THIS zip name only (preserves other regions' zips) 156 - | 157 if [ -n "${PACKAGE_ID}" ]; then 158 FILE_IDS=$(curl --silent --fail --header "JOB-TOKEN: ${CI_JOB_TOKEN}" \ 159 "${CI_API_V4_URL}/projects/${CI_PROJECT_ID}/packages/${PACKAGE_ID}/package_files" \ 160 | jq -r --arg name "${ZIP_NAME}" '.[] | select(.file_name == $name) | .id') 161 for fid in ${FILE_IDS}; do 162 echo "Deleting stale file id ${fid} (${ZIP_NAME})" 163 curl --silent --fail --request DELETE \ 164 --header "JOB-TOKEN: ${CI_JOB_TOKEN}" \ 165 "${CI_API_V4_URL}/projects/${CI_PROJECT_ID}/packages/${PACKAGE_ID}/package_files/${fid}" 166 done 167 fi 168 169 # Upload the new zip 170 - | 171 curl --fail --header "JOB-TOKEN: ${CI_JOB_TOKEN}" \ 172 --upload-file "${ZIP_NAME}" \ 173 "${CI_API_V4_URL}/projects/${CI_PROJECT_ID}/packages/generic/${PACKAGE_NAME}/latest/${ZIP_NAME}"