Plugin Documentation

MultiplayerStack
Accounts, profiles and matchmaking on AWS

One plugin for the online backbone of a multiplayer game: Amazon Cognito player accounts, Amazon DynamoDB player profiles, stats and leaderboards, and Amazon GameLift FlexMatch matchmaking — wired together so a game can go from sign-in to a match with a handful of Blueprint nodes. Built on the official AWS SDK for C++.

v1.0
UE 4.27 & 5.8
Win64, Linux & Android
83 Blueprint nodes
Category Networking
Alpha XP

Overview

MultiplayerStack covers the same features as the Alpha XP plugins CognitoPass, DynamoLedger and GameLiftMatch in a single plugin with one shared AWS connection, one set of credentials and one settings page — plus combined nodes that connect the three areas. It can be installed next to those plugins: every module, class and setting has its own name.

  • Player (combined): Sign In And Connect signs the player in to the user pool, gets identity-pool credentials for the DynamoDB and GameLift calls and creates or loads the player profile — in one node. Restore Session And Connect, Connect Player, Sign Out Everywhere, Get Player Id, Get Player Name.
  • Profile (combined): one DynamoDB item per player keyed by the player id, with rating, wins / losses / draws, numeric stats and text fields. Ensure / Load / Save Player Profile, Update Player Stats (atomic), Get Leaderboard, Record Match Result with an Elo rating update and the pure Calculate Elo.
  • Matchmake (combined): Matchmake With Profile sends the player's rating and region latencies to FlexMatch; Find Match And Travel also travels to the server; Cancel Matchmaking.
  • Login: Amazon Cognito user pools — sign-up, sign-in with challenges and MFA, authenticator apps, password reset, attributes, remembered sessions with automatic refresh, AWS credentials.
  • Data: Amazon DynamoDB with plain JSON — items, queries, scans, batches, transactions, atomic counters, leaderboards, {IdentityId} tokens.
  • Match: Amazon GameLift for the game client — FlexMatch, queue placement, session search and creation, region latencies, connect URLs.
  • MultiplayerStack Subsystem events: On Signed In, On Signed Out, On Session Refreshed, On Profile Loaded, On Match Found, On Matchmaking Failed.

Requirements

RequirementDetails
Unreal Engine4.27 and 5.8
PlatformsWin64, Linux and Android
ModulesMultiplayerStack (Runtime), MultiplayerStackSdk (prebuilt AWS SDK for C++ 1.11.916 in Source/ThirdParty: cognito-idp, cognito-identity, dynamodb, gamelift)
DependenciesNo other plugins. On Linux and Android the SDK uses the engine's libcurl, OpenSSL and certificate store.
AWSAn AWS account with a Cognito user pool and identity pool, a DynamoDB table for profiles and (for matchmaking) a GameLift fleet with a FlexMatch configuration. Usage is billed by AWS.

Installation

  1. Install MultiplayerStack from Fab into your engine, or copy the MultiplayerStack folder into your project's Plugins folder.
  2. Enable MultiplayerStack in Edit > Plugins and restart the editor.
  3. Open Project Settings > Plugins > MultiplayerStack and set User Pool Id, App Client Id, Identity Pool Id, Profile Table and Default Matchmaking Configuration. Region can stay empty (it is read from the user pool id).
  4. C++ only: add PublicDependencyModuleNames.Add("MultiplayerStack"); to your Build.cs.
Next to other AWS pluginsMultiplayerStack carries its own copy of the SDK under a plugin-specific name and uses its own class names, log category (LogMultiplayerStack), config section and SaveGame slot, so it installs side by side with the other Alpha XP cloud plugins, including the standalone CognitoPass, DynamoLedger and GameLiftMatch.

Setting up AWS

1. User pool

In Amazon Cognito create a user pool and an app client with the ALLOW_USER_PASSWORD_AUTH and ALLOW_REFRESH_TOKEN_AUTH flows (preferably without a client secret). Copy the pool id (for example us-east-1_AbCdEf123) and the client id into the Login settings.

2. Identity pool

Create an identity pool and add the user pool as an identity provider (user pool id + app client id). Enable guest access if players may play before signing in. Signed-in players are registered with the pool automatically; their identity id is the player id of every area.

3. Profile table

Table mygame-prod-players       (on-demand capacity)
  PlayerId  String  partition key   = the player id (Cognito identity id)

Global secondary index Rating-index    (one per stat you rank by: Wins-index, xp-index ...)
  partition key  Board   (String)      every profile has Board = "global"
  sort key       Rating  (Number)
  projection     INCLUDE PlayerName (or ALL)

Set Profile Table to players and Table Prefix to mygame-prod- (or the full name with an empty prefix). The key name, the leaderboard partition attribute and the index name pattern are settings.

4. Matchmaking

Upload your dedicated server, create a fleet (and an alias), a game session queue, a FlexMatch rule set and a matchmaking configuration. For Matchmake With Profile the rule set needs a Number attribute named like Rating Attribute Name (default skill), for example:

"playerAttributes": [{ "name": "skill", "type": "number", "default": 1000 }],
"rules": [{ "name": "FairSkill", "type": "distance", "measurements": ["avg(teams[*].players.attributes[skill])"],
            "referenceValue": "avg(flatten(teams[*].players.attributes[skill]))", "maxDistance": 200 }]

5. Role policy

Attach this policy to the role the identity pool gives to players (authenticated and/or guest). The first statement only allows the player's own profile item (the partition key must be the caller's identity id), the second lets everyone read the leaderboard indexes, the third allows the GameLift client actions.

{
  "Version": "2012-10-17",
  "Statement": [
    {
      "Sid": "OwnProfileOnly",
      "Effect": "Allow",
      "Action": [
        "dynamodb:GetItem", "dynamodb:BatchGetItem", "dynamodb:Query",
        "dynamodb:PutItem", "dynamodb:UpdateItem", "dynamodb:DeleteItem",
        "dynamodb:BatchWriteItem", "dynamodb:ConditionCheckItem"
      ],
      "Resource": "arn:aws:dynamodb:us-east-1:123456789012:table/mygame-prod-players",
      "Condition": {
        "ForAllValues:StringEquals": {
          "dynamodb:LeadingKeys": ["${cognito-identity.amazonaws.com:sub}"]
        }
      }
    },
    {
      "Sid": "ReadLeaderboards",
      "Effect": "Allow",
      "Action": "dynamodb:Query",
      "Resource": "arn:aws:dynamodb:us-east-1:123456789012:table/mygame-prod-players/index/*"
    },
    {
      "Sid": "Matchmaking",
      "Effect": "Allow",
      "Action": [
        "gamelift:StartMatchmaking", "gamelift:DescribeMatchmaking",
        "gamelift:StopMatchmaking", "gamelift:AcceptMatch",
        "gamelift:StartGameSessionPlacement", "gamelift:DescribeGameSessionPlacement",
        "gamelift:StopGameSessionPlacement", "gamelift:SearchGameSessions",
        "gamelift:DescribeGameSessions", "gamelift:CreateGameSession",
        "gamelift:CreatePlayerSession"
      ],
      "Resource": "*"
    }
  ]
}

Remove the actions your game does not call (FlexMatch games only need the first four GameLift actions). User-pool calls (sign-in, sign-up, MFA, attributes) need no IAM permissions: they are authenticated by the app client and the player's tokens.

Never ship access keysStatic keys in the settings end up in DefaultGame.ini and in packaged games. Use them only for development and dedicated servers; players should always use the identity pool. Shipping builds refuse settings keys unless Allow Static Keys In Shipping is enabled.

Quick start

Sign in, profile, match

  1. Main menu: call Restore Session And Connect. On Success = the returning player is signed in and Profile is loaded; On Failure with NoSavedSession = show the login screen.
  2. Login screen: Sign In And Connect with user name and password. On Challenge (MFA code, new password): answer with Respond To Challenge, then call Connect Player. New players use Sign Up / Confirm Sign Up first.
  3. Show Get Player Name and Profile > Rating; bind UI to the subsystem's On Profile Loaded so it updates by itself.
  4. Play button: Find Match And Travel (Configuration Name empty = the settings default). The player's Rating goes to FlexMatch, latencies are measured, and when the match is ready the player travels to host:port?PlayerSessionId=.... On Requires Acceptance: call Accept Match with Ticket.TicketId. A Cancel button calls Cancel Matchmaking on the subsystem.
  5. After the match: Record Match Result (Win / Loss / Draw, the opponent's rating) and Update Player Stats (for example kills = 12, xp = 300).
  6. Leaderboard screen: Get Leaderboard (Stat Rating, Count 10) → rows with Rank, Player Name, Score and Is Local Player.
  7. Settings menu: Sign Out Everywhere.

Your dedicated server must validate each player: read PlayerSessionId from the login options and accept it through GameLift's server-side AcceptPlayerSession call, rejecting the login when that fails.

Results should come from the serverRecord Match Result and Update Player Stats run with the player's own credentials, so a modified client could report a win it did not earn. For competitive games, let the dedicated server (Static Keys or Default Credential Chain on the server role) or a backend function write results, and give players read access only.

Player profiles

A profile is one item in the Profile Table, keyed by the player id (the Cognito identity id). Fixed attributes: PlayerName, Rating, Wins, Losses, Draws, MatchesPlayed, CreatedAt, UpdatedAt (ISO-8601 UTC) and the leaderboard partition attribute (Board = "global"). Every other number attribute appears in Stats, every other text attribute in Attributes; the whole item is in Item JSON, so the Data nodes work on the same item too.

{ "PlayerId": "us-east-1:7a3c...", "PlayerName": "Ada", "Rating": 1016.4, "Wins": 3, "Losses": 1, "Draws": 0,
  "MatchesPlayed": 4, "Board": "global", "kills": 41, "xp": 1200, "avatar": "fox",
  "CreatedAt": "2026-10-29T18:02:11.000Z", "UpdatedAt": "2026-10-29T19:40:03.000Z" }
  • New profiles get Default Rating (1000) and Default Stats. Ensure Player Profile uses a conditional write, so it is safe to call on every start.
  • Update Player Stats is one atomic ADD; Record Match Result increments the counters atomically and writes the new rating only when the rating did not change since it was read (retried up to four times).
  • Elo: Expected = 1 / (1 + 10^((Opponent - Player) / 400)), New = Player + K * (Score - Expected), Score 1 / 0.5 / 0, K = Elo K Factor (32). Ratings are rounded to 0.01 and never go below 0.
  • Guest and signed-in players have different identity ids, so a guest's profile does not carry over to the account automatically.

Nodes: Player, Profile, Matchmake

The combined nodes. Latent nodes can be stopped with Cancel on their return value and fire exactly one final pin on the game thread.

NodeKindInputsOutputsNotes
Sign In And ConnectLatentUsername, PasswordOn Success / On Failure (Session, Profile, Error), On Challenge (Challenge Name, Challenge Parameters)Sign In + identity-pool credentials + Ensure Player Profile (when Ensure Profile On Connect). On Failure with a valid Session: signed in, but credentials or profile failed.
Restore Session And ConnectLatent—On Success / On Failure (Session, Profile, Error)Restore Session (SaveGame slot MultiplayerStackSession) + credentials + profile. NoSavedSession when there is none.
Connect PlayerLatentEnsure ProfileOn Success / On Failure (Session, Profile, Error)Credentials + profile for the current player: after Respond To Challenge, Set Login Token, or for guests.
Sign Out EverywhereLatent—On Success / On Failure (Error)Cancels matchmaking, global sign-out (all devices), clears session, remembered session, identity login and cached profile (even when the server call fails).
Get Player IdPure—Player IdThe identity id, else the signed-in player's sub.
Get Player NamePure—NameCached profile's Player Name, else the user name.
Ensure Player ProfileLatentPlayer NameOn Success / On Failure (Profile, Created, Error)Creates the profile with the defaults unless it exists; returns it either way.
Load Player ProfileLatent—On Success / On Not Found / On Failure (Profile, Error)Strongly consistent read of the player's profile.
Save Player ProfileLatentProfileOn Success / On Failure (Profile, Error)Replaces the whole item; Player Id is always the current player.
Update Profile AttributesLatentFields (map)On Success / On Failure (Profile, Error)Sets text fields (PlayerName, avatar ...) without touching the rest.
Update Player StatsLatentStat Deltas (map name → number)On Success / On Failure (Profile, Error)Atomic ADD of every delta; negative values subtract. Needs an existing profile.
Get LeaderboardLatentStat, Count; advanced: Descending, Index NameOn Success / On Failure (Entries, Error)Query on "<Stat>-index" (Board = global). Entries: Rank, Player Id, Player Name, Score, Is Local Player, Item JSON.
Record Match ResultLatentOutcome (Win / Loss / Draw), Opponent Rating; advanced: K FactorOn Success / On Failure (Profile, Rating Delta, Error)Counters + Elo rating update with an optimistic check.
Calculate EloPurePlayer Rating, Opponent Rating, Outcome; advanced: K FactorNew Rating, Rating Delta, Expected ScoreThe same formula, without a request.
Get Cached Player ProfilePureTarget: MultiplayerStack SubsystemProfileThe profile last loaded or written (Valid = false before that).
Matchmake With ProfileLatentConfiguration Name, Latencies; advanced: Team, Extra Attributes, Poll Interval, Max Wait SecondsOn Status Changed, On Requires Acceptance; On Matched / On Failed (Ticket, Error)FlexMatch with Rating as Rating Attribute Name (Number) + Extra Attributes. Empty Latencies = measured now. Cancel stops the ticket. One matchmaking at a time.
Find Match And TravelLatentPlayer Controller, Configuration Name, Latencies; advanced: Team, Extra Attributes, Extra Options, Prefer Dns Name, Poll Interval, Max Wait SecondsSame pins as Matchmake With ProfileOn Matched fires, then ClientTravel to the connect URL. No address / player controller = On Failed with TravelFailed.
Cancel MatchmakingCallableTarget: MultiplayerStack SubsystemReturn: was one runningStops the running Matchmake With Profile / Find Match And Travel and its ticket.
Is MatchmakingPureTarget: MultiplayerStack SubsystemReturn valueTrue while one of them is waiting.

Nodes: Config & Identity

Shared by all areas (one region, one set of credentials).

NodeKindInputsOutputsNotes
Set RegionCallableRegion—Region of every following request (empty = from the User Pool Id).
Set Credential ModeCallableMode—Overrides the settings at runtime.
Set Login TokenCallableProvider, Token—Identity-pool login with another provider (Google, Apple, Facebook, OpenID). Not needed after Sign In.
Clear Login TokensCallable——Forgets the logins and the identity (the player becomes a guest).
Set Static CredentialsCallableAccess Key Id, Secret Access Key, Session Token—Static Keys mode with keys from your backend.
Get Identity IdPure—Identity IdEmpty until credentials were resolved once.
Make User Pool Provider NamePureRegion, User Pool IdProvidercognito-idp.<region>.amazonaws.com/<pool id>.
Is ConfiguredPure—Return, ProblemChecks the SDK, user pool, app client, region and credential settings.
Resolve IdentityLatentForce RefreshOn Success / On Failure (Identity Id, Error)Fetches identity and credentials now.
CancelCallableTarget: any latent node—None of its pins fire any more (matchmaking nodes also stop their ticket).
Is FinishedPureTarget: any latent nodeReturn valueTrue after it finished or was cancelled.

Nodes: Login (Amazon Cognito user pools)

NodeKindInputsOutputsNotes
Sign UpLatentUsername, Password, Email; advanced: AttributesOn Success / On Failure (User Confirmed, Code Delivery Destination, Error)Attribute names are Cognito's: name, preferred_username, phone_number, custom:team ...
Confirm Sign UpLatentUsername, CodeOn Success / On Failure (Error)Confirms the account.
Resend Confirmation CodeLatentUsernameOn Success / On Failure (Code Delivery Destination, Error)Masked destination, for example a***@e***.com.
Sign InLatentUsername, PasswordOn Success (Session, Error), On Challenge (Challenge Name, Challenge Parameters), On FailureUSER_PASSWORD_AUTH. The ID token is registered with the identity pool automatically.
Respond To ChallengeLatentChallenge Name, ResponsesSame pins as Sign InNEW_PASSWORD_REQUIRED, SMS_MFA, SOFTWARE_TOKEN_MFA, EMAIL_OTP, SELECT_MFA_TYPE; the key CODE maps to the right one.
Restore SessionLatent—On Success / On Failure (Session, Error)Remembered refresh token (Remember Session). A rejected token is deleted.
Refresh SessionLatent—On Success / On Failure (Session, Error)Renews the tokens now (Auto Refresh does it before expiry).
Sign OutLatentGlobalOn Success / On Failure (Error)Global = all devices. Local and remembered session are always cleared.
Forgot PasswordLatentUsernameOn Success / On Failure (Code Delivery Destination, Error)Sends a reset code.
Confirm Forgot PasswordLatentUsername, Code, New PasswordOn Success / On Failure (Error)Sets the new password.
Change PasswordLatentOld Password, New PasswordOn Success / On Failure (Error)Signed in.
Get User AttributesLatent—On Success / On Failure (Attributes, Error)sub, email, email_verified, custom attributes ...
Update User AttributesLatentAttributesOn Success / On Failure (Code Delivery Destination, Error)A changed e-mail / phone number needs Verify User Attribute.
Verify User AttributeLatentAttribute Name, CodeOn Success / On Failure (Code Delivery Destination, Error)Empty Code = send a new code.
Delete AccountLatent—On Success / On Failure (Error)Deletes the player from the pool and signs out.
Setup Authenticator AppLatent—On Success / On Failure (Secret Code, Otp Auth Uri, Error)otpauth:// URI for a QR code; also during an MFA_SETUP challenge.
Verify Authenticator AppLatentCode; advanced: Friendly NameOn Success / On Failure (Error)Makes the app the preferred MFA; completes an MFA_SETUP sign-in.
Get AWS CredentialsLatent—On Success / On Failure (Credentials, Error)The player's temporary AWS keys (identity pool), or the static keys / default chain.
Is Signed InPure—Return valueTrue while a session exists.
Get SessionPure—SessionUsername, Sub, Id Token, Access Token, Expires At, Valid.
Get Token ClaimsPureTokenReturn, Claims, JsonJWT payload; the signature is not checked.
Get User Pool Provider NamePure—Return valueThe identity-pool login key of the configured user pool.

Nodes: Data (Amazon DynamoDB)

Items are plain JSON; {IdentityId} inside any string value is replaced with the player id. Plain table names get the Table Prefix.

NodeKindInputsOutputsNotes
Put ItemLatentTable, Item JSON, Condition Expression; advanced: Return Old, Values JSON, Names JSONOn Success / On Condition Failed / On Failure (Old Item JSON, Error)Writes or replaces a whole item.
Get ItemLatentTable, Key JSON; advanced: Projection Expression, Consistent Read, Names JSONOn Success / On Not Found / On Failure (Item JSON, Error)Reads one item by key.
Update ItemLatentTable, Key JSON, Update Expression, Values JSON; advanced: Names JSON, Condition ExpressionOn Success (Updated JSON), On Condition Failed, On FailureSET / REMOVE / ADD / DELETE; returns the item after the update.
Delete ItemLatentTable, Key JSON; advanced: Condition Expression, Values JSON, Names JSONOn Success / On Condition Failed / On Failure (Old Item JSON, Error)Deletes one item and returns it.
QueryLatentTable, Key Condition, Values JSON; advanced: Names JSON, Index Name, Filter Expression, Limit, Scan Forward, Start Key JSONOn Success / On Failure (Items JSON, Next Start Key JSON, Count, Error)One page of a partition; pass Next Start Key JSON back for the next page.
ScanLatentTable, Filter Expression, Values JSON; advanced: Names JSON, Limit, Start Key JSON, Segment, Total SegmentsOn Success / On Failure (Items JSON, Next Start Key JSON, Count, Error)Page by page; parallel scan with segments.
Batch GetLatentTable, Keys JSONOn Success / On Failure (Items JSON, Error)100 per request, unprocessed keys retried; order of the keys.
Batch WriteLatentTable, Put Items, Delete KeysOn Success / On Failure (Written Count, Error)25 per request with retries; not atomic.
Transact WriteLatentOperations JSON; advanced: Client TokenOn Success / On Failure (Error)Up to 100 put / update / delete / check operations, all or nothing.
Increment CounterLatentTable, Key JSON, Attribute, DeltaOn Success / On Failure (New Value, Error)Atomic; nested paths such as stats.kills.
Get Top ScoresLatentTable, Index Name, Partition Key Name, Partition Value, Count, DescendingOn Success / On Failure (Items JSON, Error)Generic leaderboard query on any table.
Make Key JSONPureName, Value, Sort Name, Sort Value; advanced: Sort Value Is NumberReturn value{"pk":"{IdentityId}","sk":"inventory"}.
Struct To JSONCallableStruct (any)Return, JsonReady to use as Item JSON.
JSON To StructCallableJsonReturn, Out Struct (any)Missing fields keep their defaults.
Get JSON FieldPureJson, PathReturn, ValuePath such as inventory[2].count.

Nodes: Match (Amazon GameLift)

NodeKindInputsOutputsNotes
Find MatchLatentConfiguration Name, Players, Latencies; advanced: Poll Interval, Max Wait SecondsOn Status Changed, On Requires Acceptance; On Matched / On Failed (Ticket, Error)Start Matchmaking + Wait For Match; Cancel stops the ticket.
Start MatchmakingLatentConfiguration Name, Players, Latencies; advanced: Ticket IdOn Success / On Failure (Ticket, Error)Players empty = one player with the identity id.
Wait For MatchLatentTicket Id; advanced: Poll Interval, Max Wait Seconds, Stop Ticket On CancelOn Status Changed, On Requires Acceptance; On Matched / On FailedPolls the ticket; transient errors are retried up to 5 times in a row.
Accept MatchLatentTicket Id, Player Ids, AcceptOn Success / On Failure (Error)Player Ids empty = this player.
Stop MatchmakingLatentTicket IdOn Success / On Failure (Error)Cancels a ticket.
Start Game Session PlacementLatentQueue Name, Max Players, Game Session Name, Game Properties, Players, Latencies; advanced: Placement Id, Game Session DataOn Success / On Failure (Placement, Error)New session through a queue.
Wait For PlacementLatentPlacement Id; advanced: Poll Interval, Max Wait Seconds, Stop Placement On CancelOn Placed / On Failed (Placement, Error)Until Fulfilled, Cancelled, Timed Out or Failed.
Stop Game Session PlacementLatentPlacement IdOn Success / On Failure (Placement, Error)Cancels a pending placement.
Search Game SessionsLatentFilter Expression, Sort Expression, Limit; advanced: Next Token, Fleet Id, Alias Id, LocationOn Success / On Failure (Sessions, Next Token, Error)Server browser; 20 per page.
Describe Game SessionsLatentGame Session Id; advanced: Status Filter, Next Token, Fleet Id, Alias Id, Location, LimitOn Success / On Failure (Sessions, Next Token, Error)One session or all sessions of a fleet / alias.
Create Game SessionLatentMax Players, Name, Game Properties; advanced: Fleet Id, Alias Id, Location, Game Session Data, Idempotency Token, Wait Until ActiveOn Success / On Failure (Session, Error)Direct session on a fleet; waits until active by default.
Create Player SessionLatentGame Session Id, Player Id; advanced: Player DataOn Success / On Failure (Connection, Error)Reserves a slot and returns the address.
Measure Region LatenciesLatentRegions; advanced: Samples, Timeout SecondsOn Success / On Failure (Latencies, Best Region, Failed Regions)TCP connect times to every region at the same time, fastest first.
Make Connect URLPureConnection, Player Id; advanced: Extra Options, Prefer Dns NameReturn valuehost:port?PlayerSessionId=psess-...
Travel To Game SessionCallablePlayer Controller, Connection, Player Id; advanced: Extra Options, Prefer Dns NameReturn, UrlMake Connect URL + ClientTravel.
Get Best RegionPureLatenciesReturn, Latency MsFastest region of a latency map.

Subsystem events

Get Game Instance Subsystem > MultiplayerStack Subsystem, then bind:

EventKindFires when
On Signed In (Session)EventSign In, Respond To Challenge, Restore Session, Verify Authenticator App (MFA_SETUP) or a combined sign-in signed a player in.
On Signed OutEventSign Out, Sign Out Everywhere, Delete Account, or the user pool rejected the refresh token.
On Session Refreshed (Session)EventRefresh Session or an automatic refresh renewed the tokens.
On Profile Loaded (Profile)EventA profile node (or a connect / matchmake node) loaded, created or changed the profile.
On Match Found (Ticket)EventMatchmake With Profile / Find Match And Travel found a match.
On Matchmaking Failed (Ticket, Error)EventThey ended without a match (failed, timed out, cancelled on AWS, travel failed). Not for Cancel.

Credentials

ModeUse forHow
Cognito Identity PoolGame clientsGuests get unauthenticated credentials; after Sign In (or Set Login Token) the player gets the authenticated role. Tokens and credentials are renewed automatically before they expire. Guest identities are remembered across restarts.
Static KeysDevelopment, dedicated servers, keys from your backendSettings keys or Set Static Credentials. There is no identity id: the player id falls back to the user-pool sub.
Default Credential ChainServers and toolsEnvironment variables, the ~/.aws profile, ECS and EC2 instance roles.

User-pool requests (the Login area) are always unsigned; the Data and Match areas and Get AWS Credentials use the mode above. All areas share one region, one worker pool and one SDK instance.

C++ API

// Build.cs: PublicDependencyModuleNames.Add("MultiplayerStack");
#include "MultiplayerStackGlueAsyncActions.h"

UMultiplayerStackSignInAndConnectAction* Connect = UMultiplayerStackSignInAndConnectAction::SignInAndConnect(this, User, Password);
Connect->OnSuccess.AddDynamic(this, &UMyLoginWidget::HandleConnected);   // (Session, Profile, Error)
Connect->OnFailure.AddDynamic(this, &UMyLoginWidget::HandleConnectFailed);
Connect->Activate();

UMultiplayerStackFindAndTravelAction* Play = UMultiplayerStackFindAndTravelAction::FindMatchAndTravel(this, nullptr, FString(), FString(),
    TMap<FString, FMultiplayerStackMatchAttribute>(), FMultiplayerStackMatchLatencyMap(), TMap<FString, FString>());
Play->OnFailed.AddDynamic(this, &UMyLobbyWidget::HandleNoMatch);
Play->Activate();

Every latent node class has a static factory with the node's inputs; bind the delegates, then call Activate(). Area headers: MultiplayerStackLoginAsyncActions.h, MultiplayerStackDataAsyncActions.h, MultiplayerStackMatchAsyncActions.h; libraries: MultiplayerStackLibrary.h, MultiplayerStackGlueLibrary.h, MultiplayerStackLoginLibrary.h, MultiplayerStackDataLibrary.h, MultiplayerStackMatchLibrary.h.

Types

TypeKindMembers
FMultiplayerStackPlayerProfileStructPlayer Id, Player Name, Rating, Wins, Losses, Draws, Matches Played, Stats, Attributes, Created At, Updated At, Item JSON, Valid
FMultiplayerStackLeaderboardEntryStructRank, Player Id, Player Name, Score, Is Local Player, Item JSON
EMultiplayerStackMatchOutcomeEnumWin, Loss, Draw
FMultiplayerStackLoginSessionStructUsername, Sub, Id Token, Access Token, Expires At (UTC), Valid
FMultiplayerStackLoginAwsCredentialsStructIdentity Id, Access Key Id, Secret Access Key, Session Token, Expiration
FMultiplayerStackLoginStringMapStructValues (challenge parameters, user attributes)
FMultiplayerStackMatchPlayerStructPlayer Id, Team, Attributes, Latency Ms, Player Data
FMultiplayerStackMatchAttributeStructType, String Value, Number Value, String List, Number Map
FMultiplayerStackMatchLatencyMapStructValues (region → ms)
FMultiplayerStackMatchTicketStructTicket Id, Configuration Name, Status, Status Reason, Status Message, Estimated Wait Seconds, Player Ids, Connection
FMultiplayerStackMatchPlacementStructPlacement Id, Queue Name, Status, Game Session Name, Connection
FMultiplayerStackMatchConnectionStructGame Session Id, Ip Address, Dns Name, Port, Region, Player Sessions
FMultiplayerStackMatchPlayerSessionStructPlayer Id, Player Session Id
FMultiplayerStackMatchGameSessionStructGame Session Id, Name, Fleet Id, Status, Current / Max Players, Accepts New Players, Ip Address, Dns Name, Port, Location, Creator Id, Game Properties, Game Session Data
FMultiplayerStackErrorStructCode, Message, Http Status, Retryable
EMultiplayerStackCredentialModeEnumCognito Identity Pool, Static Keys, Default Credential Chain
EMultiplayerStackMatchTicketStatus / PlacementStatus / SessionStatus / AttributeTypeEnumAs in the GameLift API (Queued, Searching, Requires Acceptance, Placing, Completed, Failed, Cancelled, Timed Out ...)
UMultiplayerStackSubsystemClassGame Instance Subsystem with the events above, Cancel Matchmaking, Is Matchmaking, Get Cached Player Profile

Settings

Project Settings > Plugins > MultiplayerStack (saved to DefaultGame.ini, section [/Script/MultiplayerStack.MultiplayerStackSettings]). Changes apply to the next request.

SettingDefaultDescription
Connection: Region(empty)Region of all resources; empty = from the User Pool Id, then the Identity Pool Id, then us-east-1.
Connection: Request / Connect Timeout Ms30000 / 5000Time limits per request.
Connection: Max Retries, Worker Threads3, 4Retries with back-off; background threads.
Connection: Verify SSL, Log Sdk WarningsOn, OnTLS checks; SDK warnings to LogMultiplayerStack.
Credentials: Credential ModeCognito Identity PoolSource of the Data / Match credentials.
Credentials: Identity Pool Id, Allow Guest Access(empty), OnFor example us-east-1:01234567-89ab-cdef-0123-456789abcdef.
Credentials: Access Key Id / Secret Access Key, Allow Static Keys In Shipping(empty), OffStatic Keys mode (development and servers).
Login: User Pool Id, App Client Id, App Client Secret(empty)The user pool and its app client (secret only if the client has one).
Login: Remember Session, Auto RefreshOn, OnSaveGame slot MultiplayerStackSession; renew tokens about 5 minutes before expiry.
Login: Login Endpoint Override(empty)A local user-pool emulator.
Data: Table Prefix, Consistent Reads By Default(empty), OffPrefix for plain table names; strongly consistent reads.
Data: Data Endpoint Override(empty)For example DynamoDB Local (http://localhost:8000).
Player Profile: Profile Table, Profile Key Nameplayers, PlayerIdThe profile table and its partition key.
Player Profile: Ensure Profile On ConnectOnThe connect nodes create / load the profile.
Player Profile: Default Rating, Elo K Factor, Default Stats1000, 32, (empty)Values of new profiles and the rating update.
Leaderboard: Partition Key, Partition Value, Index FormatBoard, global, {stat}-indexHow Get Leaderboard finds the index.
Match: Default Matchmaking Configuration, Default Queue Name, Default Fleet Id / Alias Id(empty)Used when a node leaves them empty.
Match: Poll Interval Seconds10Status checks of the wait / matchmaking nodes.
Match: Rating Attribute NameskillFlexMatch Number attribute filled with the profile's Rating.
Match: Match Endpoint Override(empty)A local test service.
Latency: Latency Regions, Host Format, Port15 regions, gamelift.{region}.amazonaws.com, 443Where latency is measured.

Troubleshooting

Error codeCause and fix
NotConfiguredA required setting is empty (User Pool Id, App Client Id, Identity Pool Id, Profile Table, Leaderboard Partition Key). Call Is Configured for the details.
NotAuthorizedExceptionWrong password, a disabled user, guest access off on the identity pool, or a token that expired.
AccessDeniedExceptionThe identity pool role lacks the DynamoDB or GameLift permission, or the profile key is not the caller's identity id (LeadingKeys).
NoProfileThe player has no profile yet: call Ensure Player Profile (the connect nodes do it with Ensure Profile On Connect).
NoPlayerIdNo identity id and nobody signed in: use the Cognito Identity Pool credential mode or sign in first.
ValidationException (leaderboard)The index does not exist or its keys differ: create "<Stat>-index" with partition key Board and the stat as Number sort key.
RatingConflictThe rating changed four times in a row while recording a result; try again.
MatchmakingFailed / MatchmakingTimedOut / WaitLimitFlexMatch found no match within its timeout, or Max Wait Seconds was reached. Check the rule set's attributes (Rating Attribute Name) and latency rules.
TravelFailedA match was found but there was no player controller or address. Pass a Player Controller to Find Match And Travel.
UnavailableThe SDK library could not be loaded or the engine is shutting down. Check the Output Log for LogMultiplayerStack errors.

Credits

© 2026 Alpha XP — alphaxp.net · Support: support@alphaxp.net. Includes the AWS SDK for C++ and the AWS Common Runtime (Apache License 2.0). Built for Unreal Engine 4.27 and 5.8.