Protocol Documentation
neosu uses and extends the bancho protocol.
While no official documentation exists, here is a great reference: https://github.com/Lekuruu/bancho-documentation/wiki.
Whenever "convars" or "variables" are mentioned, this means in-game variables, accessible by pressing Shift+F1.
The full list of variables is available here. This should give you a nice idea of how customizable neosu is for server admins.
You do NOT have to implement any of the features below; neosu will gracefully fallback to "vanilla" behavior.
Detect neosu clients via header on c. endpoint:
x-mcosu-ver: <version>
            API endpoints use this user agent:
Mozilla/5.0 (compatible; neosu/<version info>; +https://neosu.net/)
        Enable score submission with header:
x-mcosu-features: submit=1
            
            PROTECTED variables.PROTECTED. Use the UNPROTECT_VARIABLES packet for allowing individual mods and features.
            OAuth authentication is automatically enabled for:
neosu.localneosu.netssl_verify convar to 0 for neosu.local
            Implements OAuth 2.0 Authorization Code flow with PKCE.
When clicking the "Log in with osu!" button, neosu will open the browser to:
GEThttps://neosu.net/connect/start?challenge={b64(sha256(verification_bytes))}
The server should then generate an URL-safe code, which will be forwarded to neosu by having the player click on a link:
neosu://login/neosu.net/{code}
            neosu will make a request to get the refresh token:
GEThttps://neosu.net/connect/finish?code={code}&proof={b64(verification_bytes)}
We use the c. endpoint login packet, with:
$oauthServer returns cho-token like for regular clients.
After logging in, neosu will attempt to connect to wss://c.neosu.net/ws/. If the server returns a different HTTP code than 101, neosu will fall back to HTTP polling, like regular clients.
If you're planning to add support for websockets on your server, remember to treat websocket connections the same as a polling client: CloudFlare tends to close websocket connections after 2 minutes, so a connection closing does not mean the client has actually stopped playing.
In requests where the username and password hash are passed as parameters, username will be $token and password hash will be {cho-token}.
This includes score submission, where the username is passed and hashed in the score data.
Submitted scores have an extra neosu-mods section, containing base64-encoded data representing neosu-specific mods.
Requests: neosu has a "Team" leaderboard filter, which sets the parameter v=5 (as opposed to, say, v=4 for "Country").
Responses: Score lines have an extra section after the "has_replay" flag, containing base64-encoded data representing neosu-specific mods.
POSThttps://osu.neosu.net/web/neosu-submit-map.php
Server should verify that the map md5 matches the file data.
128 PROTECT_VARIABLESMarks variables as PROTECTED. Score submission disabled when value differ from defaults.
129 UNPROTECT_VARIABLESRemoves PROTECTED flag. Scores submit regardless of variable value.
130 FORCE_VALUESForces variables to specific values.
131 RESET_VALUESResets variables to client-side value.
132 REQUEST_MAPRequests an .osu file from the client. Used for unranked/unavailable maps.
Client should send the .osu file to the neosu-submit-map endpoint.