Comment on page
Understanding Steam Authentication, when and why to use it ... and when and why not to.
The above link and repeated below so you can find it: https://partner.steamgames.com/doc/features/auth Is highly important, that you should fully read Valve's own documentation around Steam Authentication to fully understand it. Some of the information will be summarized herein and notes on the tools and systems Heathen has created around Steam Authentication.
Heathen's Authentication API handles both Client and Server authentication and manages the ticket and session data generated for you.
You will notice that unlike other APIs there is no Client or Server or Web version. Because the Steam API endpoints have the same requirements and signatures for all targets we are able to select the correct endpoint for you based on the build type.
That is for a client or "normal" build we will use the Client endpoints and for a server build or "headless" build we will use the Server endpoints.
The intended use of Steam Authentication is that the subject who wishes to authenticate ... typically a user. Will generate a "Ticket"
Authentication.GetAuthSessionTicket(identity, (ticket, IOError) =>
This ticket contains a bit of information but the important part is the data represented as a byte
This is the data that should be sent to whoever or whatever it is that will be authenticating this subject. So send it to your game server or your peer if you doing peer-to-peer authentication ... and yes peer-to-peer authentication can be done.
How exactly you send the ticket is between you and your networking tool or your lobby system.
For example in a Peer to Peer game where you are using Steam Inventory items, you may want to validate that all members of a lobby do really own the items they claim to own. You can use Steam Authentication for this by starting an authentication session between each user and sending a serialized copy of the inventory items. Steam clients can then validate that yes they are owned and who they are owned by.
In any case, you will need to send 2 bits of information being
- 1.The user ID of the user who generated the ticket
- 2.The byte e.g. "Ticket Data" that was generated
Each ticket can be used exactly once and does expire after some time. So for example, if you want to have every peer in a P2P game authenticate every other peer then every player will need to generate 1 ticket for every other player and will need to validate 1 ticket from every other player.
void AuthenticatUser(byte ticket, UserData user)
var responce = Authentication.BeginAuthSession(ticket, user, result =>
//All is well
//This user is not connected to Steam
//This user is not licensed for this game
//This user is VAC banned for this app
//This session is logged elsewhere
//This VAC Check is timed out, may be fine, may not
//This Tickedt cancelled by the owner
//This publisher issued ban
//This Ticket invalid / already used
//This Ticket invalid
//Send correctly, wait for callback
//Invalid ticket will get no response
//Duplicate requests will get no response
//Invalid version will get no response
//Game mismatch will get no response
//Expired ticket, will get no response
This simply takes in the ticket and user ID that generated it and asks Steam API to validate it. The results of this call will tell you whether or not it's valid and will give you details about the authenticated user such as whether or not they are VAC banned, how exactly they own a license to the App they are authenticating from and for, etc.
Having authenticated a user allows for a few additional features. For example, a Steam Game Server identifies the users playing on it by what Auth Sessions are active. That is when you Begin Auth Session for a user you are telling Valve that said user is playing on that server, when you end the session you are telling Valve that the user is no longer playing.
void UserLoggedOff(UserData user)
When a game session is done you should notify Valve that the session is over by ending the auth session.
A common use for authentication sessions is to validate that a given user owns specific inventory items. This can only be done once an Authentication Session has been started with that user. This can be done on Client to Client or Client to Server.
You can either serialize the local user's whole inventory (rare)
or you can serialize specific items (more common)
In either case, the result is a byte of data that represents the inventory state at the time of serialization, who that inventory was read from and when it was read.
//Assume that instanceIds is the collection of items you want to send
Inventory.Client.SerializeItemResultsByID(instanceIds, data =>
Once you have this byte you should send it to who or whatever it is that needs to validate ownership of the items.
The specifics of sending the data are between you and your networking tools, the important thing is that you are sending 2 bits of data
- 1.The user ID that generated the serialized inventory data
- 2.The data itself
When your peer or server receives this data they can read its details
void ValidateInventory(UserData user, byte data)
Inventory.Client.DeserializeResult(user, data, responce =>
if(responce.result == EResult.k_EResultOK)
Debug.Log(user.Nickname + " owns these " + items.length + " items");
else if(responce.result == EResult.k_EResultExpired)
Debug.LogWarning(user.Nickname + " owns them, but this data is old.");