Broadleaf Microservices
  • v1.0.0-latest-prod

Auth Release Notes for 2.3.0-GA

Tip
The 2.x versions are Spring Boot 3 compatible.

Requirements

  • Spring Authorization Server 1.5.6+ is required for this version of AuthenticationServices, and beyond

Important Updates

Spring Boot Upgrade

  • As of Broadleaf Release Train 2.3.0-GA, all microservices have been upgraded to support Spring Boot 3.3 & 3.5.

New Features & Notable Changes

Spring Authorization Server Upgrade

AuthenticationServices is built upon and customizes various functionality from Spring Authorization Server.

In typical release cycles, the underlying version of Spring Authorization Server is upgraded via the standard Broadleaf base dependencies upgrades, and does not necessarily result in any changes to AuthenticationServices itself.

In this release, however, a multitude of classes in AuthenticationServices have been updated to reach full parity with the recently released Spring Authorization Server 1.5.6 version.

The overwhelming majority of changes around this are just simple internal refactorings to align with similar changes in Spring Authorization Server itself. From a functional perspective, there should be no significant differences in the behavior of the application.

With that being said, there are a handful of new features in Spring Authorization Server (SAS) such as OAuth2 Demonstrating Proof of Possession (DPoP) and Pushed Authorization Requests (PAR). While Broadleaf does not explicitly leverage or customize these flows, at the very least, the changes in this release give the relevant Broadleaf components the foundation for future support.

Below is a list of key affected classes. In all of them, there have been changes made to respond to SAS’s refactoring and eliminate redundant code.

  • OIDAwareOAuth2RefreshTokenAuthenticationProvider

    • DPoP support

  • PublicRefreshOAuth2AuthorizationCodeAuthenticationProvider

    • Updated comments/Javadocs to explain the customizations in context of the new SAS

    • DPoP support

  • ScopeNarrowingOAuth2AuthorizationCodeRequestAuthenticationProvider

    • PAR support

    • Native OIDC prompt support

  • ScopeNarrowingOAuth2ClientCredentialsAuthenticationProvider

    • DPoP support

    • The base SAS class introduced a new authenticationValidator concept to validate scopes, but our customizations require a different approach, so this is disabled by default.

  • PublicRefreshPublicClientAuthenticationProvider

    • Aligns with stricter PKCE enforcement around codeVerifier from newer SAS versions

  • PublicRefreshCodeVerifierAuthenticator

    • Aligns with stricter PKCE enforcement around codeVerifier from newer SAS versions

    • Aligns with fail-fast behavior from SAS when code was missing in an authorization_code flow

  • AdvancedOAuth2RefreshTokenConfigurerUtils

    • SAS introduced some new 'default' token customizers relate to DPoP and Token Exchange delegation, which are now successfully registered in addition to the standard token customizers from Broadleaf.

  • DefaultClientScopeAuthorizationCodeRequestConverter

    • PAR support

  • DefaultOAuth2AuthorizationCodeRequestAuthenticationValidator

    • Updated with new methods matching changes in SAS for use in other components

  • EmbeddedLoginCodeAuthenticationProvider

    • Updated to maintain full parity with updates in PublicRefreshOAuth2AuthorizationCodeAuthenticationProvider and the latest SAS

Third Party Login Improvements

  • Introduced a new OAuth2LoginSystemAuthenticationFailureExceptionMapping bean responsible for handling system (not user) errors that occur on 3PIDP login requests.

    • This means if the 3PIDP setup is misconfigured in any way (ex: invalid client secret, etc), the end user will now see an accurate error message stating there is an internal system error rather than an issue with the user’s input.

    • The handler will also emit error logs detailing the issue, since such logs were not already being emitted by the Spring components implementing the login flow.

  • When a third party IDP client registration is defined in both the DB and in properties, the system will now disallow admin (API) requests to modify the DB-based registration. Property-defined client registration information now always takes precedence when specified, so mutating the DB-based representation would not have any effect anyway. In order to mutate the DB representation, any system configuration properties related to that registration must be fully removed from the environment. This validation prevents users from being confused about their changes to the DB representation not actually taking effect.

  • Excluded issuerUri from OAuthClientRegistration equals/hashcode, as the database representation never has a value for this field, and thus causes unnecessary mismatches to be detected between the property and DB representations of a client registration

  • Introduced changes to allow 3PIDP configurations to specify initial values for tenant/app access when auto-registering users whose tenant/app access is not managed externally

    • Introduced new provider-specific configuration properties to allow AuthenticationServices to set initial values for tenant/app access on auto-registered admin users when external management is disabled. Please see the configuration properties documentation for more details

      • Previously this was only per app type (e.g., only per Admin or Application).

    • Updated AbstractExternalAdminUserHandler to defer to these internally set properties when external management is disabled. If the external property values are not set, access defaults to no-access just as before.

      Example Configuration
      broadleaf:
        auth:
          user:
            web:
              authorization:
                identity-provider:
                  admin:
                    # original setting, applies to all admin apps
                    # auto-register: true
                    providers:
                      okta:
                        # new per provider setting
                        auto-register: true
                        icon: /img/okta-icon.svg
                      google:
                        # new per provider setting
                        auto-register: false
                        icon: /img/google-icon.svg
  • Added 3rd party IDP claims to access token

    • Previously they were only on the session token.

    • This allows them to be known in the UI and acted on such as to make a user’s email read-only if they signed in with Google.

  • Added support for syncing Account numbers to Auth

    • This is a modification to the CustomerAccount domain.

Miscellaneous

  • Property broadleaf.auth.token.support-refresh-token-rotation was removed and whether refresh token support is enabled is now solely based on AuthorizedClient/RegisteredClient grant types(REFRESH_TOKEN)

    • For example: registeredClient.getAuthorizationGrantTypes().contains(AuthorizationGrantType.REFRESH_TOKEN)

  • Property broadleaf.auth.token.support-refresh-token-cleanup removed.

  • Introduced the new property broadleaf.auth.token.enable-oauth2-authorization-cleanup. This property would default to true. This property controls whether a clean-up job to prune obsolete OAuth2Authorizations (runs periodically) is enabled. This property supersedes the now-removed broadleaf.auth.token.support-refresh-token-cleanup property.

  • Added an event listener that will prune the blc_password_token table as it can grow large over time.

  • Added official support for Caffeine and Ehcache as alternative caching providers for many microservices.

    • This includes new auto-configuration and properties for managing heap and off-heap budgets, as well as weights and estimated sizes for various service components.

    • For more details on configuring these providers, see the Caching Configuration documentation.

  • Updated scheduled jobs to support more user-friendly duration formats (e.g., 2d, 12h) in addition to ISO-8601.

    • Additionally, these jobs now emit started and completed events to provide better visibility into their execution status.

  • Introduced lots of new diagnostic trace logs in OAuth2 flows to make it easier to identify the root cause that failed a request. You can now enable TRACE logs in any of the following classes, and more detailed information will appear as the request moves through the flow.

    Note
    This is primarily intended only for use in lower environments, and in scenarios where testing a new integration may temporarily require extra diagnostic output. It’s not recommended to enable these logs in production, as they will be very noisy.
    Note
    The API responses returned to the external caller have not changed - the messages there still remain vague to prevent leaking information to potential attackers.
    • com.broadleafcommerce.auth.authorization.security.embedded.code.EmbeddedLoginCodeAuthenticationConverter

    • com.broadleafcommerce.auth.authorization.security.embedded.code.EmbeddedLoginCodeAuthenticationProvider

    • com.broadleafcommerce.auth.authorization.security.spring.OIDAwareOAuth2RefreshTokenAuthenticationProvider

    • com.broadleafcommerce.auth.authorization.security.spring.PublicRefreshCodeVerifierAuthenticator

    • com.broadleafcommerce.auth.authorization.security.spring.PublicRefreshOAuth2AuthorizationCodeAuthenticationProvider

    • com.broadleafcommerce.auth.authorization.security.spring.PublicRefreshPublicClientAuthenticationProvider

    • com.broadleafcommerce.auth.authorization.security.spring.ScopeNarrowingOAuth2AuthorizationCodeRequestAuthenticationProvider

    • com.broadleafcommerce.auth.authorization.security.spring.ScopeNarrowingOAuth2ClientCredentialsAuthenticationProvider

  • Refactored AuthenticationFailureExceptionMapping/DefaultExceptionMappingAuthenticationFailureHandler to support more complex code-based error handling determinations rather than purely relying on an exception name. Furthermore, AuthenticationFailureExceptionMapping can now define a bean order, which allows defining a priority of the mapping recognized by DefaultExceptionMappingAuthenticationFailureHandler

    • Existing AuthenticationFailureExceptionMapping beans will continue to work as expected for backward compatibility.

  • Add explicit AuthenticationFailureExceptionMapping bean for the UsernameNotFoundException to produce a more useful error message when that exception is thrown

  • The Application’s logo is now displayed on the login form if available

  • Add logic to filter out questionable permissions for customers in auth. See Customer Authority Filter

  • Introduce cache(oauth2IdentityProviders) for oauth2 identity providers instead of Map. You can control its ttl with property broadleaf.auth.cache.oauth2-identity-providers-cache, default is 5 mins.

  • Now when a DB(blc_oauth_client_registration) and a property file(spring.security.oauth2.client.registration.xxx) have the same entry for client registration, the one from a property file will be used.

  • Removed Yugabyte liquibase generation support, as it is no longer a supported DB.

  • Added support for user restrictions to be discriminated by account ID.

  • Added support to be able to display an Application’s logo on the login form.

  • Optimized the space efficiency of restrictions / restricted authorities in access tokens.

  • Added support to be able to update a user’s restrictions, restricted roles, and restricted permissions upon receiving an AccountMemberRestrictionUpdateEvent event.

  • Added support to persist a user in the Authentication Service from the Account User Creation Flow.

    • Updated Customer representation to properly deserialize the ID and ContextState when emitted from Customer Service with the actual Customer object (as opposed to PersistenceMessage payload)

    • Introduce CustomerPersistenceUtil to handle some common logic related to customer persistence

    • Added consumer events and bindings to listen for events emitted from Customer Service related to customer persistence, such as when a new customer is created and needs to be persisted in Auth

    • Note that the reason why the event is named AccountUserManuallyCreatedEvent instead of just AccountUserCreatedEvent is to be explicitly clear that this is specifically emitted & processed when an account user is manually created by another account user, rather than by the system through the account invite flow

  • Added support to emit audit events for user lifecycle changes such as user creation, deletion, and login/logout events.

New Seed Data

  • Added permissions/scopes for the new Fee domain added to Pricing Services. See Pricing Services 2.2.0 Release Notes for more information. These changelogs are included in the auth.starter.required.data.changelog.xml file.

    • Introduced FEE permissions and scopes

    • Granted the cartsopsclient the ALL_FEE permission/scopes

    • Added openapi client scope and permission for FEE

    • Granted the FEE user permissions to default Admin roles such as FULL_ACCESS, PARTIAL_ACCESS, APPLICATION_ACCESS, ROLE_MARKETPLACE_OPERATOR, ROLE_VENDOR_ADMIN, and ROLE_VENDOR_MERCHANDISER

  • Added permissions/scopes for the new fulfillment callback endpoints in Cart Operation Services and Payment Transaction Services. These changelogs are included in the auth.starter.required.data.changelog.xml file.

    • Introduced FULFILLMENT_PAYMENT_CALLBACK and EXTERNAL_FULFILLMENT_CALLBACK permissions and scopes

    • Granted the cartopsclient the FULFILLMENT_PAYMENT_CALLBACK scope

    • Granted the anonymous client the EXTERNAL_FULFILLMENT_CALLBACK scope

    • Added openapi client scope and permission for FULFILLMENT_PAYMENT_CALLBACK and EXTERNAL_FULFILLMENT_CALLBACK

  • Granted the cartsopsclient the SYSTEM_SAVED_PAYMENT_MANAGEMENT scope and READ_SYSTEM_SAVED_PAYMENT_MANAGEMENT permission

    • This is needed to read the available saved payment methods summary to validate the subscription payment by CartPaymentMethodValidationActivity during checkout

  • Added permissions/scopes for the new concepts of Cost and Adjustment price lists.

    • Introduced COST_LIST and ADJUSTMENT_LIST permissions and scopes.

    • Added an openapi client scope and permission for COST_LIST and ADJUSTMENT_LIST.

    • Granted the COST_LIST and ADJUSTMENT_LIST user permissions to default Admin roles such as FULL_ACCESS, PARTIAL_ACCESS, APPLICATION_ACCESS, and ROLE_MARKETPLACE_OPERATOR

  • Added missing security scopes and permission mappings for Customer operations such as CUSTOMER_RETURN, CUSTOMER_ORDER, and CUSTOMER_ENTITLEMENT.

  • Created a separate permission to allow Admins to modify their own preferences.

    • Introduced ADMIN_USER_PROFILE permissions and scopes.

    • Added an openapi client scope and permission for ADMIN_USER_PROFILE.

    • Granted the ADMIN_USER_PROFILE user permissions to default Admin roles such as FULL_ACCESS, PARTIAL_ACCESS, APPLICATION_ACCESS, ROLE_MARKETPLACE_OPERATOR, ROLE_VENDOR_ADMIN, and ROLE_VENDOR_MERCHANDISER

  • Added scopes and permissions to restrict which users can modify Cart internal attributes.

    • Introduced CART_INTERNAL_ATTRIBUTE permissions and scopes.

    • Added an openapi client scope and permission for CART_INTERNAL_ATTRIBUTE.

  • Added an authorized client & permissions/scopes for operations related to the newly introduced Billing Services and Subscription Operations Services.

    • Introduced a new billingclient authorized client mapped with the ACCOUNT_SUBSCRIPTION, BILLING, CUSTOMER_SUBSCRIPTION, REFUND_TRANSACTION_RESULTS, SAVED_PAYMENT_METHOD_EXECUTE_AUTHORIZE_AND_CAPTURE, SAVED_PAYMENT_METHOD_TRANSACTION_RESULTS, SUBSCRIPTION, SYSTEM_SAVED_PAYMENT_MANAGEMENT, and SYSTEM_SUBSCRIPTION and scopes & permissions.

    • Introduced a new subscriptionopsclient authorized client mapped with the ADMIN_SCOPED_SERVICE_CLIENT, CART_INTERNAL_ATTRIBUTE, CUSTOMER, CUSTOMER_SEGMENT, OFFER, ORDER, SUBSCRIPTION, SYSTEM_SUBSCRIPTION scopes & permissions.

    • Mapped the SUBSCRIPTION_PRICING, SYSTEM_SAVED_PAYMENT_MANAGEMENT and SYSTEM_SUBSCRIPTION scopes & permissions to the cartopsclient authorized client.

    • Mapped the ADMIN_SCOPED_SERVICE_CLIENT, BILLING, DELETE_SUBSCRIPTION, OFFER, PRICE_LIST, SUBSCRIPTION, and SYSTEM_SUBSCRIPTION scopes & permissions to the workflowclient authorized client.

    • Granted the BILLING, SUBSCRIPTION, and ACCOUNT_SUBSCRIPTION user permissions to default Admin roles such as FULL_ACCESS and PARTIAL_ACCESS.

    • Granted the CUSTOMER_SUBSCRIPTION user permission to the default Customer User role.

  • Added permissions/scopes for access to the Cancellation Policy feature.

    • Introduced CANCELLATION_POLICY permissions and scopes.

    • Added an openapi client scope and permission for CANCELLATION_POLICY.

    • Granted the CANCELLATION_POLICY user permission to default Admin roles such as FULL_ACCESS and PARTIAL_ACCESS.

    • Mapped the CANCELLATION_POLICY scope & permission to the cartopsclient and `authorized clients.

  • Added permissions/scopes for the pricingclient and notificationclient to read order and order fulfillment data.

    • Granted the pricingclient the ORDER_FULFILLMENT scope and READ_ORDER_FULFILLMENT permission.

    • Granted the notificationclient the ORDER and ORDER_FULFILLMENT scopes and READ_ORDER and READ_ORDER_FULFILLMENT permissions.

Bug Fixes

  • AuthServiceUserWebAutoConfiguration.addResourceHandlers was previously misconfigured with invalid resource paths, which caused failures starting in Spring Boot 3.5 due to stricter Spring validations. The resource configuration has been reworked with corrected syntax and more granular mappings. From an external perspective, nothing has changed, and resources can still be accessed at the same paths as before (so templates will be unaffected).

  • Fixed a compilation issue related to the Thymeleaf upgrade.

  • Fixed a channel name typo in PurgePasswordTokenJobListener.

  • Fixed an error when the AccountMemberRoleChangeRequest#userId or AccountMemberRestrictionUpdateEvent#userId is null.

  • Fixed bug in AccountMemberRestrictionChangeRequestHandler where the restrictions field was incorrectly being cleared instead of the actual roles and permissions fields

    • When restricted roles or restricted permissions are empty in the event payload, the restrictions field is being cleared instead of the appropriate user field for roles or permissions.

  • Fixed message for the UserNotActiveException thrown when a user is deactivated while already logged in.

  • Fixed an issue where the creation of an Authorized Client with a name longer than 36 characters would fail due to the name being too long for the database column.