From ce6472a6872b286406e447994336938296537b06 Mon Sep 17 00:00:00 2001 From: Norman Lansing Date: Fri, 3 Apr 2026 20:34:49 -0400 Subject: [PATCH] Lesson 76 - Parsing the Game Session Response --- FPSTemplate.uproject.DotSettings.user | 2 + .../Private/UI/HTTP/HTTPRequestTypes.cpp | 40 +++++++++- .../Private/UI/Portal/PortalManager.cpp | 43 ++++++++++- .../UI/Portal/Signin/SignInOverlay.cpp | 8 +- .../Public/UI/APITest/APITestManager.h | 2 +- .../Public/UI/HTTP/HTTPRequestTypes.h | 73 +++++++++++++++++++ .../Public/UI/Portal/PortalManager.h | 2 +- .../Public/UI/Portal/Signin/SignInOverlay.h | 2 +- 8 files changed, 166 insertions(+), 6 deletions(-) create mode 100644 FPSTemplate.uproject.DotSettings.user diff --git a/FPSTemplate.uproject.DotSettings.user b/FPSTemplate.uproject.DotSettings.user new file mode 100644 index 00000000..c6ab21b4 --- /dev/null +++ b/FPSTemplate.uproject.DotSettings.user @@ -0,0 +1,2 @@ + + ForceIncluded \ No newline at end of file diff --git a/Source/DedicatedServers/Private/UI/HTTP/HTTPRequestTypes.cpp b/Source/DedicatedServers/Private/UI/HTTP/HTTPRequestTypes.cpp index 1d84a2e3..3cea3ec7 100644 --- a/Source/DedicatedServers/Private/UI/HTTP/HTTPRequestTypes.cpp +++ b/Source/DedicatedServers/Private/UI/HTTP/HTTPRequestTypes.cpp @@ -1,6 +1,11 @@ #include "UI/HTTP/HTTPRequestTypes.h" #include "DedicatedServers/DedicatedServers.h" +namespace HTTPStatusMessages +{ + const FString SomethingWentWrong{TEXT("Something went wrong...")}; +} + void FDSMetaData::Dump() const { UE_LOGFMT(LogDedicatedServers, Log, "MetaData:"); @@ -21,6 +26,39 @@ void FDSListFleetsResponse::Dump() const if (!NextToken.IsEmpty()) { - UE_LOGFMT(LogDedicatedServers, Log, "NextToken: {NextToken}", NextToken); + UE_LOGFMT(LogDedicatedServers, Log, "NextToken: {NextToken}", *NextToken); } } + +void FDSGameSession::Dump() const +{ + UE_LOGFMT(LogDedicatedServers, Log, "GameSession:"); + + UE_LOGFMT(LogDedicatedServers, Log, "GameSessionId: {GameSessionId}", *GameSessionId); + UE_LOGFMT(LogDedicatedServers, Log, " Name: {Name}", *Name); + UE_LOGFMT(LogDedicatedServers, Log, " FleetArn: {FleetArn}", *FleetArn); + UE_LOGFMT(LogDedicatedServers, Log, " CreationTime: {CreationTime}", CreationTime); // need to write a conversion function + UE_LOGFMT(LogDedicatedServers, Log, " TerminationTime: {TerminationTime}", TerminationTime); // need to write a conversion function + UE_LOGFMT(LogDedicatedServers, Log, " CurrentPlayerSessionCount: {CurrentPlayerSessionCount}", CurrentPlayerSessionCount); + UE_LOGFMT(LogDedicatedServers, Log, " MaximumPlayerSessionCount: {MaximumPlayerSessionCount}", MaximumPlayerSessionCount); + UE_LOGFMT(LogDedicatedServers, Log, " Status: {Status}", *Status); + UE_LOGFMT(LogDedicatedServers, Log, " StatusReason: {StatusReason}", *StatusReason); + + UE_LOGFMT(LogDedicatedServers, Log, " GameProperties:"); + for (const TTuple GameProperty : GameProperties) + { + UE_LOGFMT(LogDedicatedServers, Log, " {Key} : {Value}", *GameProperty.Key, *GameProperty.Value); + } + + UE_LOGFMT(LogDedicatedServers, Log, " IpAddress: {IpAddress}", *IpAddress); + UE_LOGFMT(LogDedicatedServers, Log, " DnsName: {DnsName}", *DnsName); + UE_LOGFMT(LogDedicatedServers, Log, " Port: {Port}", Port); + UE_LOGFMT(LogDedicatedServers, Log, " PlayerSessionCreationPolicy: {PlayerSessionCreationPolicy}", *PlayerSessionCreationPolicy); + UE_LOGFMT(LogDedicatedServers, Log, " CreatorId: {CreatorId}", *CreatorId); + UE_LOGFMT(LogDedicatedServers, Log, " GameSessionData: {GameSessionData}", *GameSessionData); + UE_LOGFMT(LogDedicatedServers, Log, " MatchmakerData: {MatchmakerData}", *MatchmakerData); + UE_LOGFMT(LogDedicatedServers, Log, " Location: {Location}", *Location); + UE_LOGFMT(LogDedicatedServers, Log, " ComputeName: {ComputeName}", *ComputeName); + UE_LOGFMT(LogDedicatedServers, Log, " PlayerGatewayStatus: {PlayerGatewayStatus}", *PlayerGatewayStatus); + +} diff --git a/Source/DedicatedServers/Private/UI/Portal/PortalManager.cpp b/Source/DedicatedServers/Private/UI/Portal/PortalManager.cpp index 5702fb52..e9e54522 100644 --- a/Source/DedicatedServers/Private/UI/Portal/PortalManager.cpp +++ b/Source/DedicatedServers/Private/UI/Portal/PortalManager.cpp @@ -4,12 +4,15 @@ #include "UI/Portal/PortalManager.h" #include "HttpModule.h" +#include "JsonObjectConverter.h" #include "Data/API/APIData.h" #include "GameplayTags/DedicatedServerTags.h" +#include "Interfaces/IHttpResponse.h" +#include "UI/HTTP/HTTPRequestTypes.h" void UPortalManager::JoinGameSession() { - BroadcastJoinGameSessionMessage.Broadcast(TEXT("Searching for Game Session...")); + BroadcastJoinGameSessionMessage.Broadcast(TEXT("Searching for Game Session..."), false); check(APIData); @@ -28,4 +31,42 @@ void UPortalManager::FindOrCreateGameSession_Response(FHttpRequestPtr Request, F bool bWasSuccessful) { GEngine->AddOnScreenDebugMessage(-1, 5.f, FColor::Red, TEXT("Find or Create Game Session Response Received")); + + if (!bWasSuccessful) + { + BroadcastJoinGameSessionMessage.Broadcast(HTTPStatusMessages::SomethingWentWrong, true); + } + + TSharedPtr JsonObject; + TSharedRef> JsonReader = TJsonReaderFactory<>::Create(Response->GetContentAsString()); + if (FJsonSerializer::Deserialize(JsonReader, JsonObject)) + { + if (ContainsErrors(JsonObject)) + { + BroadcastJoinGameSessionMessage.Broadcast(HTTPStatusMessages::SomethingWentWrong, true); + } + DumpMetadata(JsonObject); + + if (JsonObject->HasField(TEXT("GameProperties"))) + { + auto PropertiesArray = JsonObject->GetArrayField(TEXT("GameProperties")); + TSharedPtr FlatMapJson = MakeShareable(new FJsonObject); + + for (auto& PropJson : PropertiesArray) + { + auto PropObj = PropJson->AsObject(); + FString Key = PropObj->GetStringField(TEXT("Key")); + FString Value = PropObj->GetStringField(TEXT("Value")); + FlatMapJson->SetStringField(Key, Value); + } + // Replace the array with a flat map field + JsonObject->SetObjectField(TEXT("GameProperties"), FlatMapJson); + } + + + FDSGameSession GameSession; + FJsonObjectConverter::JsonObjectToUStruct(JsonObject.ToSharedRef(), &GameSession); + GameSession.Dump(); + BroadcastJoinGameSessionMessage.Broadcast(TEXT("Found Game Session."), false); + } } diff --git a/Source/DedicatedServers/Private/UI/Portal/Signin/SignInOverlay.cpp b/Source/DedicatedServers/Private/UI/Portal/Signin/SignInOverlay.cpp index 308c329e..b37a1758 100644 --- a/Source/DedicatedServers/Private/UI/Portal/Signin/SignInOverlay.cpp +++ b/Source/DedicatedServers/Private/UI/Portal/Signin/SignInOverlay.cpp @@ -30,8 +30,14 @@ void USignInOverlay::OnJoinGameButtonClicked() JoinGameWidget->Button_JoinGame->SetIsEnabled(false); } -void USignInOverlay::UpdateJoinGameStatusMessage(const FString& StatusMessage) +void USignInOverlay::UpdateJoinGameStatusMessage(const FString& StatusMessage, const bool bShouldResetJoinGameButton) { check(IsValid(JoinGameWidget)); + check(IsValid(JoinGameWidget->Button_JoinGame)); JoinGameWidget->SetStatusMessage(StatusMessage); + + if (bShouldResetJoinGameButton) + { + JoinGameWidget->Button_JoinGame->SetIsEnabled(true); + } } diff --git a/Source/DedicatedServers/Public/UI/APITest/APITestManager.h b/Source/DedicatedServers/Public/UI/APITest/APITestManager.h index 814f9805..b480aa5d 100644 --- a/Source/DedicatedServers/Public/UI/APITest/APITestManager.h +++ b/Source/DedicatedServers/Public/UI/APITest/APITestManager.h @@ -7,7 +7,7 @@ #include "UI/HTTP/HTTPRequestManager.h" #include "APITestManager.generated.h" -DECLARE_DYNAMIC_MULTICAST_DELEGATE_TwoParams(FOnListFleetsResponseReceived, const FDSListFleetsResponse&, ListFleetsResponse, bool, bWasSuccessful); +DECLARE_DYNAMIC_MULTICAST_DELEGATE_TwoParams(FOnListFleetsResponseReceived, const FDSListFleetsResponse&, ListFleetsResponse, const bool, bWasSuccessful); /** diff --git a/Source/DedicatedServers/Public/UI/HTTP/HTTPRequestTypes.h b/Source/DedicatedServers/Public/UI/HTTP/HTTPRequestTypes.h index 4bfbefdd..53441e3a 100644 --- a/Source/DedicatedServers/Public/UI/HTTP/HTTPRequestTypes.h +++ b/Source/DedicatedServers/Public/UI/HTTP/HTTPRequestTypes.h @@ -2,6 +2,11 @@ #include "HTTPRequestTypes.generated.h" +namespace HTTPStatusMessages +{ + extern DEDICATEDSERVERS_API const FString SomethingWentWrong; +} + USTRUCT() struct FDSMetaData { @@ -33,5 +38,73 @@ struct FDSListFleetsResponse UPROPERTY() FString NextToken; + void Dump() const; +}; + +USTRUCT() +struct FDSGameSession +{ + GENERATED_BODY() + + UPROPERTY() + FString GameSessionId{}; + + UPROPERTY() + FString Name{}; + + UPROPERTY() + FString FleetArn{}; + + UPROPERTY() + double CreationTime{}; + + UPROPERTY() + double TerminationTime{}; + + UPROPERTY() + int32 CurrentPlayerSessionCount{}; + + UPROPERTY() + int32 MaximumPlayerSessionCount{}; + + UPROPERTY() + FString Status{}; + + UPROPERTY() + FString StatusReason{}; + + UPROPERTY() + TMap GameProperties{}; + + UPROPERTY() + FString IpAddress{}; + + UPROPERTY() + FString DnsName{}; + + UPROPERTY() + int32 Port{}; + + UPROPERTY() + FString PlayerSessionCreationPolicy{}; + + UPROPERTY() + FString CreatorId{}; + + UPROPERTY() + FString GameSessionData{}; + + UPROPERTY() + FString MatchmakerData{}; + + UPROPERTY() + FString Location{}; + + UPROPERTY() + FString ComputeName{}; + + UPROPERTY() + FString PlayerGatewayStatus{}; + void Dump() const; }; \ No newline at end of file diff --git a/Source/DedicatedServers/Public/UI/Portal/PortalManager.h b/Source/DedicatedServers/Public/UI/Portal/PortalManager.h index 54b6f974..6c1f1c7b 100644 --- a/Source/DedicatedServers/Public/UI/Portal/PortalManager.h +++ b/Source/DedicatedServers/Public/UI/Portal/PortalManager.h @@ -7,7 +7,7 @@ #include "UI/HTTP/HTTPRequestManager.h" #include "PortalManager.generated.h" -DECLARE_DYNAMIC_MULTICAST_DELEGATE_OneParam(FBroadcastJoinGameSessionMessage, const FString&, StatusMessage); +DECLARE_DYNAMIC_MULTICAST_DELEGATE_TwoParams(FBroadcastJoinGameSessionMessage, const FString&, StatusMessage, bool, bShouldResetJoinGameButton); /** * diff --git a/Source/DedicatedServers/Public/UI/Portal/Signin/SignInOverlay.h b/Source/DedicatedServers/Public/UI/Portal/Signin/SignInOverlay.h index 6d465d6a..3757ae52 100644 --- a/Source/DedicatedServers/Public/UI/Portal/Signin/SignInOverlay.h +++ b/Source/DedicatedServers/Public/UI/Portal/Signin/SignInOverlay.h @@ -39,5 +39,5 @@ private: void OnJoinGameButtonClicked(); UFUNCTION() - void UpdateJoinGameStatusMessage(const FString& StatusMessage); + void UpdateJoinGameStatusMessage(const FString& StatusMessage, const bool bShouldResetJoinGameButton); };