CS2 share code decode failed: the fix.
A CS2 match share code is CSGO- plus 25 characters from a 57-character alphabet. Decode it by reversing the characters, reading them as a base-57 number, writing that as 18 bytes, and reading the match ID, reservation ID and TV port little-endian. Most failures are the wrong alphabet or byte order.
- 57-character alphabet
- 18 bytes, little-endian
- Tested decoders
{ "success": true, "data": [ { "id": "cs2-match-2398974", "eventName": "ROG JOURNEY Autumn 2026", "bestOf": 3, "team1Name": "Ninjas in Pyjamas", "team2Name": "Eternal Fire", "score": { "team1": 2, "team2": 0 } }, { "id": "cs2-match-2398896", "eventName": "FOX Legacy Season 1", "bestOf": 3, "team1Name": "SAW", "team2Name": "Lazer Cats", "score": { "team1": 2, "team2": 0 } } ... ]}The error
InvalidShareCode: Invalid share code (csgo-sharecode, npm)
ValueError: not a match share code: '...' (Python decoders)
or: the code decodes, but the match ID points at nothingWhat is the CS2 share code format?
CSGO-xxxxx-xxxxx-xxxxx-xxxxx-xxxxx: five groups of five characters from the alphabet ABCDEFGHJKLMNOPQRSTUVWXYZabcdefhijkmnopqrstuvwxyz23456789. It leaves out I, O, g, l and the digits 0 and 1, which look alike. CS2 match codes still start with CSGO-.
Why does decoding fail?
Almost every broken decoder makes one of the mistakes below. The result is either an exception or a match ID that looks valid but points at nothing.
- A 62- or 64-character alphabet instead of the 57-character one.
- Not reversing the 25 characters before the base-57 conversion.
- Not left-padding the hex to 36 digits (18 bytes), which shifts every field.
- Reading the fields big-endian; each field is little-endian.
- Using 32-bit or float arithmetic: the number needs arbitrary precision (Python int, JavaScript BigInt).
- Passing a crosshair or other share code: only match codes decode to a match.
How do I decode a share code correctly?
Use the decoders below. Both are tested: CSGO-GADqf-jjyJ8-cSP2r-smZRo-TO2xK decodes to match ID 3230642215713767580, reservation ID 3230647599455273103 and TV port 55788, matching the reference implementation (akiver/csgo-sharecode).
import re
DICTIONARY = "ABCDEFGHJKLMNOPQRSTUVWXYZabcdefhijkmnopqrstuvwxyz23456789"
SHARE_CODE = re.compile(r"^CSGO(-?[" + DICTIONARY + r"]{5}){5}$")
def decode_share_code(code: str) -> dict:
code = code.strip()
if not SHARE_CODE.match(code):
raise ValueError(f"not a match share code: {code!r}")
big = 0
for c in reversed(code[4:].replace("-", "")):
big = big * len(DICTIONARY) + DICTIONARY.index(c)
raw = big.to_bytes(18, "big")
return {
"matchId": int.from_bytes(raw[0:8], "little"),
"reservationId": int.from_bytes(raw[8:16], "little"),
"tvPort": int.from_bytes(raw[16:18], "little"),
}
print(decode_share_code("CSGO-GADqf-jjyJ8-cSP2r-smZRo-TO2xK"))
# {'matchId': 3230642215713767580, 'reservationId': 3230647599455273103, 'tvPort': 55788}const DICTIONARY = "ABCDEFGHJKLMNOPQRSTUVWXYZabcdefhijkmnopqrstuvwxyz23456789"
const SHARE_CODE = new RegExp(`^CSGO(-?[${DICTIONARY}]{5}){5}$`)
export function decodeShareCode(code) {
code = code.trim()
if (!SHARE_CODE.test(code)) throw new Error(`not a match share code: ${code}`)
let big = 0n
for (const c of [...code.slice(4).replaceAll("-", "")].reverse()) big = big * 57n + BigInt(DICTIONARY.indexOf(c))
const bytes = big.toString(16).padStart(36, "0").match(/../g).map((h) => parseInt(h, 16))
const le = (from, to) => bytes.slice(from, to).reverse().reduce((acc, b) => (acc << 8n) | BigInt(b), 0n)
return { matchId: le(0, 8), reservationId: le(8, 16), tvPort: Number(le(16, 18)) }
}What can I do with the decoded IDs?
The match ID and reservation ID identify the replay, which a Steam client library can request from Valve's game coordinator to get the demo URL. The decoded values contain no scores or stats; those come from parsing the demo.
How does the CS2 API make this error impossible?
Pro matches have stable IDs such as cs2-match-2398722 that you read straight from the API, so there is no share code to decode at all. Share codes only matter for a player's own matchmaking games, which only Steam has.
curl -s "https://api.citoapi.com/api/v1/cs2/matches/results?limit=5" -H "x-api-key: $CITO_API_KEY"Frequently asked questions
Something missing? Email support@citoapi.com.
What alphabet do CS2 share codes use?
ABCDEFGHJKLMNOPQRSTUVWXYZabcdefhijkmnopqrstuvwxyz23456789: 57 characters, without I, O, g, l, 0 and 1.
What does a CS2 share code decode to?
Three numbers: the match ID (8 bytes), the reservation or outcome ID (8 bytes) and the TV port (2 bytes), each little-endian.
Do CS2 match share codes still start with CSGO-?
Yes. Match share codes kept the CSGO- prefix after the move to Counter-Strike 2.
Related
- Steam Web API for CS2 tutorialStep by step through Steam's CS2 methods, and where they stop.
- CS2 match results APIFinal series scores, map scores and box scores.
- CS2 demo parse failedWrong format, a compressed file, or a parser behind the latest patch.
- Steam Web API empty match dataWhy Steam returns no CS2 match details, and where match data lives.
- CS2 match history not foundThere is no Steam match history endpoint for CS2. What to call instead.
- How to get CS2 match dataResults, maps and player lines for any pro match in three requests.
Build CS2 live score apps
Free is for building and testing. Paid plans add commercial use, real-time live data and the full archive.