Pragma Engine 0.0.98

January 2024

Contents #

Summaries | Summarized release notes.

Full Notes | Full notes including descriptions and additional details.

Summaries #

Features #

  • [Multiplayer] New Friend service and associated Friend API for managing friend lists. | full note
  • [Multiplayer] Added ability to generate unique Partner tokens per game server. | full note
  • [Multiplayer] Player social ID now accessible on the PartyPlayer object. | full note
  • [Accounts] Added a new Data Rights service. | full note
  • [Accounts] Player Portal now available. | full note
  • [Accounts] Added a new config property to File Portal Module Plugin. | full note
  • [Player Data] All Inventory service plugins now provide access to playerId: UUID. | full note
  • [Infra & Tooling] Social Backend Partner Client Node service can now specify hostname and port to allow for multinode deployment. | full note
  • [Infra & Tooling] Load testing tools now available. | full note
  • [Portal] New web portal sign in and sign up flow. | full note
  • [Portal] You can now have multiple Portal builds. | full note
  • [Portal] Players can update their account information in the Player Portal. | full note
  • [Portal] JavaScript pragma library now extendable. | full note
  • [Portal] You can now easily configure CORS Access-Control-Allow-Origin headers for all Pragma Engine gateways. | full note

Deprecations #

  • [Multiplayer] sdk | In Unity, replace IPartyPlayer.PragmaId with IPartyPlayer.PlayerId, and PartyPlayer.PragmaId with PartyPlayer.PlayerId. | full note

Integrations #

  • [Multiplayer] sdk | For Unreal implementations, add additional include directives to the PragmaFriendApi.h and PragmaPlayerDataService.h files. | full note
  • [Mulitplayer] config | Add FriendDaoConfig to your Social config | full note
  • [Multiplayer] sdk | Rename Match API’s ReleaseCapacity to MatchApi.ReportFreedCapacity. | full note
  • [Multiplayer] sdk | If listening to the Game Loop API’s OnPlayerLeftParty event, change the signature of the listener. | full note
  • [Multiplayer] platform | Define the new ExtMatchable object. | full note
  • [Multiplayer] platform | Change the signature of the Matchmaking Plugin’s initialize method to accept a Matchmaking.Matchable instead of a Matchmaking.Party. | full note
  • [Accounts] platform, config | The Playstation identity provider has been updated to enable Portal login and account linking. | full note
  • [Infra & Tooling] platform | Update BackgroundManager function calls to include new name parameter. | full note
  • [Infra & Tooling] platform | Update uses of MetricsManager to use the new interface for tags. | full note
  • [Infra & Tooling] platform | Verify all load testing elements have been successfully built. | full note
  • [Portal] config | Update Portal configuration. | full note
  • [Portal] config | If using the module or defaultModule options for the Social Operator Gateway Node service or the Game Operator Gateway Node service, update configuration options. | full note
  • [Portal] portal, config | If using custom portlets in 5-ext/portal, update Portal folder structure. | full note
  • [SDKs] sdk | If using FConnectionInfo or FBackendConnectionInfo to retrieve connection information, modify code to use the new data types. | full note

Bugs and Fixes #

  • When the MatchmakingPlugin.Initialize method was used to bypass the matchmaking process and send a party directly to a game instance, the OnMatchmakingLeft event fired. To minimize confusion, OnMatchmakingLeft is no longer fired in this scenario.
  • The Xbox identity provider has been updated. Contact customer support for more details.
  • When a game server would call Disconnect it would only call the OnComplete delegate when it was not connected to the running Pragma backend. This could potentially cause game servers to hang, waiting for the FDisconnectedDelegate to be called. SDK: Unreal FServer::Disconnect now always executes OnComplete delegate if bound.
  • When a game client or server would call ConnectionInfo when in the state of being disconnected from Pragma Engine it would not provide any connection information. SDK: Unreal FSession::ConnectionInfo now properly populates when the connection to the platform is disconnected, both for temporary and permanent disconnects.

Docs #



Full Notes #

Features #

[Multiplayer] New Friend service and associated Friend API for managing friend lists. #

Description: Version 0.0.98 introduces the Friend service, which allows players to maintain a list of friends, and send and receive friend invites.

Details: The new Friend service includes the following resources:

  • Data classes with both private and public player information
  • Unreal SDK that supports sending invites, accepting and declining invites, removing friends, and more
  • Configuration options for friend list size and caching behavior
  • Bindable events

See the Friend service documentation for more information.

[Multiplayer] Added ability to generate unique Partner tokens per game server. #

Description: As of 0.0.98, when allocating game servers (using FleetPlugin.add or GameInstanceHostPlugin.findHostForGameInstance), you should generate a unique token for each game server and pass the token along as part of the game server allocation/instantiation request.

Details: Prior to version 0.0.98, Pragma recommended creating one Partner token that could be used by all game servers. For customers using the “find more players” or “decline reconnect” feature, this method was not optimal as it causes the platform to broadcast notifications to all game servers, even if the notification is intended for a specific individual server. With the new ability to create unique partner tokens, you can resolve this issue.

See the Fleet Management Tasks topic for instructions.

[Multiplayer] Player social ID now accessible on the PartyPlayer object. #

Description: A player’s social ID is now available on the Unreal SDK UPragmaPartyPlayer object and the Unity SDK IPartyPlayer interface. The SocialId value is useful when making various calls to the new Friend service.

See Friend Tasks for more information.

[Accounts] Added a new Data Rights service. #

Description: Operators can now start a personal data request for a specific account and monitor the status of those requests as the Data Rights service aggregates personal data from the system. This data includes linked identity providers, Social and Game identifiers, order history, friends list, and PII (such as email).

For more information, see the Add DataRightsDaoConfig to your Social config 0.0.97 integration note and Privacy Rights page.

[Accounts] Player Portal now available. #

Description: Players can now log into the Player Portal to view and manage their account data. This includes editing display name and email; this functionality is disabled by default. In addition, players can also link other accounts on supported identity providers. Identity providers that have the accountLinkingEnabled config property enabled will show up in the Linked Accounts section in the Player Portal.

Details: The local instance of the Player Portal can be found at http://localhost:11000/#/account/settings with Pragma Engine running. All identity providers that have the playerLoginEnabled config property enabled are available for Player Portal login.

To enable Player Portal authentication with each identity provider, you’ll need to add the OAuth redirect URIs. As an example, below are the URIs you will need to add to Discord’s developer console OAuth2 Redirects. This enables the localhost environment to sign in and link accounts:

  • http://localhost:11000/#/signin-discord
  • http://localhost:11000/#/link-discord

To enable this for other identity providers, you must also add similar links.

For more information on the Player Portal and available configs, see the Player Portal and Identity Provider pages.

Related notes: See new web portal sign in and sign up flow and players can update their account information in the Player Portal for more details on available features.

[Accounts] Added a new config property to File Portal Module Plugin. #

Description: The File Portal Module Plugin has an additional config property called content to support dynamic configurable content in Portal. As the first feature, we have added in a customer support link in the Player Portal so when a player’s account is linked, it will show a “Contact player support to unlink” message on the Linked Accounts page. The new config property customerSupportLink under content hyperlinks this message with your customer support link.

Details: To display a customer support link in the unlinking message, set a key and value under the content config section in the Portal.

SocialPlayerGatewayNodeService.routePlugins:
  plugins:
    Portal:
      class: "pragma.gateway.FilePortalModulePlugin"
      config:
        portalSource: "5-ext/portal/dist/player-social"
        content:
          "customerSupportLink": "http://your-company.com/support"

Related notes: See the feature note on the new Player Portal for more details.

[Player Data] All Inventory service plugins now provide access to playerId: UUID. #

Description: The InventoryData class, which belongs as a parameter for all Inventory Service Plugins, now has a field for playerId: UUID. This UUID can help author business logic for service-to-service calls and notifications based on playerIds.

[Infra & Tooling] Social Backend Partner Client Node service can now specify hostname and port to allow for multinode deployment. #

Description: You can now define the socialPartnerProtocol, socialPartnerHost, and socialPartnerPort used to make calls from Game to Social. This will allow you to successfully make HTTPS requests when Game and Social are in different nodes, such as when facilitating the syncing of entitlements for a multinode environment.

Details: In the Social Backend Partner Client Node service there are three new fields you can set in config: socialPartnerProtocol, socialPartnerHost, and socialPartnerPort.

Previously, to make HTTPS requests from Game to Social in a multinode environment you would have to make an engine mod to override the default HTTP call to be HTTPS. This new feature now makes this engine mod unnecessary. No further integration steps are required, but this configuration might be an area to revisit as you set up your platform in a multinode environment.

Example:

SocialBackendPartnerClientConfig:
   bearerToken: ""
   socialPartnerProtocol: "https"
   socialPartnerHost: "internal.pragma.com"
   socialPartnerPort: "11100"

[Infra & Tooling] Load testing tools now available. #

Description: Pragma Engine now provides comprehensive tooling for load testing your platform. This includes the ability to write scenarios to simulate the flows of your game, deploying and running your scenario at scale, and analyzing the resulting metrics with provided Grafana dashboards.

Details: For an overview of how to load test with Pragma, see the internal guide “Load testing with Pragma Overview”. For a step-by-step guide on how to set up your load test project and get started, complete the integration steps below and then follow the instructions in the README file located at 5-ext/README-LOAD-TEST.

Related notes: See integration note on load testing.

[Portal] New web portal sign in and sign up flow. #

Description: Players signing into the Player Portal can use a new sign in or sign up flow.

Details: There are two new endpoints:

  • /v1/account/authenticatev1
  • /v1/account/createaccountv1

This authentication flow is optimized for web portal sign in and sign up, and only provides social tokens. Since players will be prompted in the web portal when creating an account, this flow prevents accidental account creation.

For more information, see the Web portal sign in and sign up documentation.

[Portal] You can now have multiple Portal builds. #

Description: All Portal configuration, including custom Portal extensions and portlet directory match rules can now be specified separately for each Portal build in the Portal configuration JavaScript file.

Details: There is a new builds section for config files that allow you to overwrite configuration for a specific build. For example, if you wanted Portal extensions to appear only in the Operator Social Portal, those extensions should be moved from the root to the operator-social build section.

Example: With extensions specifically for the Operator Social Portal, your configuration could look like this:

  • Before:
module.exports = {
 common: {
    "app.extensions": ["customExtension.js"],
 },
};
  • After:
module.exports = {
  common: { ... }
  builds: {
      "operator-social": {
common: {
"app.extensions": ["customExtension.js"],
},
      }
  }
};

Related notes: See the Update Portal configuration integration note.

[Portal] Players can update their account information in the Player Portal. #

Description: Players can view and edit their display name and email address in the Player Portal on the Settings page.

Details: Players can update their display name through the UpdateDisplayNameV1 Player endpoint; this functionality is disabled by default.

To allow players to update their display name in the Player Portal, you’ll need to do the following:

  • Implement a custom Account Plugin and define display name server-side rules in the updateDisplayName function. This includes logic to prevent specific display names for vulgar language, throttle the time between updates, and other display name validation rules.
  • Enable the display name edit swappable component

Players can update their email address through the VerifyEmailV1 Player endpoint; this functionality is disabled by default. To allow players to update their email address in the Player Portal, you’ll need to do the following:

  • Implement an Email Sender Plugin
  • Enable the email edit swappable component

Players can update their email address through the VerifyEmailV1 Player endpoint; this functionality is disabled by default. To allow players to update their email address in the Player Portal, you’ll need to do the following:

  • Implement an Email Sender Plugin
  • Enable the email edit swappable component

For more information, see documentation on Manage display name and Manage email.

[Portal] JavaScript pragma library now extendable. #

Description: The global JavaScript pragma library can now be extended using the new configuration option pragmalib.extensions.

Details: The code specific to current Operator portlets has been separated out and is now available under pragma.ext.operator.

[Portal] You can now easily configure CORS Access-Control-Allow-Origin headers for all Pragma Engine gateways. #

Description: You can specify which hosts you want to allow in the CORS Access Control headers. These hosts can be configured in any Pragma Engine gateway configuration.

Example: Below is an example of how to allow only the my-domain.com domain name for the CORS access control. This assumes that the Social Player Portal will run on the domain my-domain.com. If this configuration is not specified in the CORS Access-Control-Allow-Origin header, the gateway will allow any host.

serviceConfigs:
   SocialPlayerGatewayConfig:
      corsAllowedHosts:
         1: "my-domain.com"

For more information see Hosting.

Deprecations #

[Multiplayer] sdk | In Unity, replace IPartyPlayer.PragmaId with IPartyPlayer.PlayerId, and PartyPlayer.PragmaId with PartyPlayer.PlayerId. #

Description: To align with naming conventions throughout the code base, we’ve renamed the Unity SDK value IPartyPlayer.PragmaId to IPartyPlayer.PlayerId, and PartyPlayer.PragmaId to PartyPlayer.PlayerId. Before upgrading to the next release (0.0.99), update Unity SDK code that uses these values accordingly:

originalreplacement
IPartyPlayer.PragmaIdIPartyPlayer.PlayerId
PartyPlayer.PragmaIdPartyPlayer.PlayerId

Integrations #

[Multiplayer] sdk | Add additional include directives to the PragmaFriendApi.h and PragmaPlayerDataService.h files. #

Description: To use version 0.0.98 with Unreal, add #include "Async/Future.h" to the PragmaFriendApi.h file, and #include "Containers/SortedMap.h" to the PragmaPlayerDataService.h file.

Integration steps:

  • sdk | Add the following :
    • In PragmaFriendApi.h, add: #include "Async/Future.h"
    • In PragmaPlayerDataService.h, add: #include "Containers/SortedMap.h"

Note: This is an engine modification related to a Pragma code error in 0.0.98. Manually adding the above directives will not be required in subsequent releases.

[Multiplayer] config | Add FriendDaoConfig to your Social config. #

Description: To use version 0.0.98, add the FriendDaoConfig. Any existing configs must now also define the defaults for this DaoNode for the Pragma Engine to start up properly.

Integration steps:

  • config | Under social add FriendDaoConfig:

    social:
      serviceConfigs:
        FriendDaoConfig:
          databaseConfig:
            driver: "MYSQLDB"
            username: "superuser"
            password: "password"
            hostPortSchemas: 
              1: "localhost:3306/local_social_friend"
    

[Multiplayer] sdk | Rename Match API’s ReleaseCapacity to MatchApi.ReportFreedCapacity. #

Description: The ReleaseCapacity function on the Pragma SDK Match API has been replaced by ReportFreedCapacity. The new function name better reflects what the function does, which is to report to Pragma Engine that the game server has freed up a unit of game instance capacity.

Integration steps:

  • sdk | Replace calls to ReleaseCapacity with ReportFreedCapacity:
    originalreplacement
    Unreal: MatchApi->ReleaseCapacity()Unreal: MatchApi->ReportFreedCapacity()
    Unity: MatchApi.ReleaseCapacity()Unity: MatchApi.ReportFreedCapacity()

[Multiplayer] sdk | If listening to the Game Loop API’s OnPlayerLeftParty event, change the signature of the listener. #

Description: The OnPlayerLeftParty event in the Game Loop API now broadcasts UPragmaPartyPlayer (Unreal) or IPartyPlayer (Unity), giving customers access to all player fields when they receive an OnPlayerLeftParty event, including PlayerId, SocialId, and DisplayName.

Integration steps:

  • sdk | If listening to the OnPlayerLeftParty event, change the signature of the listener according to the following table:
    originalreplacement
    Unreal: FString (PlayerPragmaId)Unreal: UPragmaPartyPlayer*
    Unity: PragmaIdUnity: IPartyPlayer

[Multiplayer] platform | Define the new ExtMatchable object. #

Description: The new ExtMatchable in the Matchmaking system can be used to store the results of in-memory calculations during the matchmaking loop. In order to compile your protos, ensure that the ExtMatchable object is defined in your 5-ext folder.

Integration steps:

  • platform | Navigate to the pragma-engine/platform/5-ext/ext-protos/src/main/protos/shared/matchmakingExt.proto file and add a message for the new ExtMatchable payload:
message ExtMatchable {
}

[Multiplayer] platform | Change the signature of the Matchmaking Plugin’s initialize method to accept a Matchmaking.Matchable instead of a Matchmaking.Party. #

Description: The MatchmakingPlugin.initialize method now accepts a Matchmaking.Matchable object instead of a Matchmaking.Party object. This change allows for access to the whole Matchable object, which includes the Matchmaking.Party as well as other data, such as the new ExtMatchable.

Integration steps:

  • platform | Change the function signature of the MatchmakingPlugin.initialize method to accept a Matchable object instead of Matchmaking.Party.
originalreplacement
initialize( queueKey: MatchmakingQueueKey, party: Matchmaking.Party):NewGameInstance?initialize( queueKey: MatchmakingQueueKey, matchable: Matchmaking.Matchable):NewGameInstance?
  • If you want to keep the previous behavior, add the following line to the top of the function: val party = matchable.parties.first()

[Accounts] platform, config | The Playstation identity provider has been updated to enable Portal login and account linking. #

Description: Contact customer support for more details.

[Infra & Tooling] platform | Update BackgroundManager function calls to include the new name parameter. #

Description: BackgroundManager has improved error logging based on a new parameter (name), which is used in the logging of errors.

Integration steps:

  • platform | Update calls to the following functions to include the new name parameter:
    originalreplacement
    fireAndForget( block: suspend CoroutineScope.() -> Unit)fireAndForget( name:String, block: suspend CoroutineScope.() -> Unit)
    fireAndForgetIO( block: suspend CoroutineScope.() -> Unit)fireAndForgetIO( name:String, block: suspend CoroutineScope.() -> Unit)
    fireAndForgetAll( collection: Collection<T>, block: suspend (T) -> Unit)fireAndForgetAll( name:String, collection: Collection<T>, block: suspend (T) -> Unit)
    parallelActor( channel: ReceiveChannel<T>, block: suspend (T) -> Unit)parallelActor( name:String, channel: ReceiveChannel<T>, block: suspend (T) -> Unit)
    serialActor( channel: ReceiveChannel<T>, block: suspend (T) -> Unit)serialActor( name:String, channel: ReceiveChannel<T>, block: suspend (T) -> Unit)

[Infra & Tooling] platform | Update uses of MetricsManager to use the new interface for tags. #

Description: We’ve updated how tags are passed into every function in the MetricsManager. Tags are no longer passed in as a list of vararg Strings, but as a list of vararg key/value pairs (Pair<String, String>). Previously if you provided an odd number of strings the last one would be dropped. This new design prevents providing a key without a value.

Integration steps:

  • platform | Update uses of MetricsManager, as shown in the following example:
    originalreplacement
    metricsManager.metricsCounter(name: String, vararg tags: String))metricsManager.metricsCounter( name: String, vararg tags: Pair<String, String>)

[Infra & Tooling] platform | Verify all load testing elements have been successfully built. #

Description: The first build of your project after upgrading to 0.0.98 will use the updated templates directory to generate several files related to the load testing tools in their correct locations. You will need to complete the listed integration steps.

Integration steps:

  • If you run into issues building the platform or running a load test, follow the steps in the 5-ext/README-LOAD-TEST file under the “But wait! 5-ext already existed!” section to verify that all elements to successfully run a load test are present.
  • Check in any newly added files.

Related notes: See feature note on load testing.

[Portal] config | Update Portal configuration. #

Description: We’ve updated how Portal building and packaging works to accommodate multiple Portal builds.

Integration steps:

  • config | Update Portal Route Plugin configurations to point to the correct Portal Operator subdirectory in the Portal build output dist directory. This will need to be done for SocialOperatorGatewayNodeService.routePlugins and GameOperatorGatewayNodeService.routePlugins.
    • Before:
     SocialOperatorGatewayNodeService.routePlugins:
      plugins:
        Portal:
          class: "pragma.gateway.FilePortalModulePlugin"
          config:
            portalSource: "portal"
    
    • After:
      SocialOperatorGatewayNodeService.routePlugins:
        plugins:
            Portal:
              class: "pragma.gateway.FilePortalModulePlugin"
              config:
                  portalSource: "portal/operator-social"
    

Related notes: See the You can now have multiple Portal builds feature note.

[Portal] config | If using the module or defaultModule options for the Social Operator Gateway Node service or the Game Operator Gateway Node service, update configuration options. #

Description: We removed the module and defaultModule options from the platform configuration for the SocialOperatorGatewayNodeService and the GameOperatorGatewayNodeService and instead, by default, always show all the portlets included in a specific build.

Integration steps:

  • config | If you don’t have custom Portal work, nothing needs to be done unless you have local or shard configuration files that specify a portalSource. If so, see next item for integration steps.
  • config | If using these configuration options to hide unused portlets, instead use the Portal extensions in your custom Portal overlay:
    1. If no custom Portal overlay exists in 5-ext/portal, create one by running the following:
    make portal-setup && make portal-init
    
    1. If you don’t need the example portlet, remove MyCustomPortlet from platform/5-ext/portal/src/portlets/operator-social/.
    2. In 5-ext/portal/src/config/default.js, uncomment the existing example or add an extension to your desired build:
    builds: {
      'operator-game': {
        common: {
          'app.extensions': ['customExtension.js']
        }
      }
    }
    
    1. In the extension (e.g., customExtension.js), update the portlet to make it always hidden:
    export default {
      portletUpdates: {
        ContentCatalogsEditor: (portlet) => portlet.isVisible(() 
          => false)
      },
    }
    

[Portal] portal, config | If using custom portlets in 5-ext/portal, update Portal folder structure. #

Description: If you have custom portlets in your 5-ext/portal/src/portlets directory (i.e. 5-ext/portal/src/portlets/MyCustomPortlet), move these portlets into the operator-social, operator-game, or player-social directory.

Integration steps:

  • portal | Move custom portlets into one of the following directories, depending on the specific use case of the portlet:
    • 5-ext/portal/src/portlets/operator-social/MyCustomPortlet
    • 5-ext/portal/src/portlets/operator-game/MyCustomPortlet
    • 5-ext/portal/src/portlets/player-social/MyCustomPortlet
  • config | If you have custom Portal work, update your Portal configurations and folder structure to account for the new build packages in the dist folder. There are now three builds included and packaged in the dist folder: operator-social, operator-game, and player-social. The default Portal configuration loads for each build are located in the respective portlets folders:
    • /src/portlets/operator-social/**
    • /src/portlets/operator-game/**
    • /src/portlets/player-social/**

[SDKs] sdk | If using FConnectionInfo or FBackendConnectionInfo to retrieve connection information, modify code to use the new data types. #

Description: We’ve updated the data types for FSession::ConnectionInfo member functions FConnectionInfo and FBackendConnectionInfo to provide more comprehensive errors.

Integration steps:

  • sdk | Update client code to use the new data types, as follows:

    • Before:
    FConnectionInfo{
    
    TOptional<EPragmaConnectionError> DisconnectError;
    
    }
    FBackendConnectionInfo{
    
    TOptional<EPragmaConnectionError> ConnectionError;
    
    }
    
    • After:
    FConnectionInfo{
    
    TOptional<FString> DisconnectError;
    
    }
    FBackendConnectionInfo{
    
    TOptional<EPragmaProtocolError> ConnectionError;
    
    }