<?xml version="1.0" encoding="UTF-8"?>
<beans xmlns="http://www.springframework.org/schema/beans"
       xmlns:util="http://www.springframework.org/schema/util"
       xmlns:sec="http://www.springframework.org/schema/security"
       xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
       xsi:schemaLocation="
          http://www.springframework.org/schema/beans http://www.springframework.org/schema/beans/spring-beans-4.3.xsd
          http://www.springframework.org/schema/util http://www.springframework.org/schema/util/spring-util-4.3.xsd
          http://www.springframework.org/schema/security http://www.springframework.org/schema/security/spring-security-6.0.xsd">
  <!-- The Spring Schemas are the latest available schemas with pinned version numbers -->
  <!-- Authentication manager configuration, specifying the class(es) responsible for performing the authentication. -->
  <sec:authentication-manager alias="authenticationManager" >
    <sec:authentication-provider ref="dummyAuthProvider"/>
  </sec:authentication-manager>

  <util:list id="authenticationProviderList">
    <ref bean="appianAuthenticationProvider"/>
    <ref bean="rememberMeAuthenticationProvider"/>
  </util:list>

  <!--
  ⚠️  Spring 6 change: AuthenticationManager is now a FactoryBean, which
      causes it to be instantiated earlier—before the transactionManager.
      Some authentication providers need an active transactional context
      during their own initialization, so this new order triggers
      “No transactional context active” startup errors.

      The workaround below defers AuthenticationManager construction
      until after the transactionManager bean is ready, restoring the
      Spring-5 initialization sequence.

      Remove this workaround only after all authentication providers are
      verified to be transaction-agnostic at startup.
-->

  <bean id="dummyAuthProvider" class="org.springframework.security.authentication.AnonymousAuthenticationProvider">
    <constructor-arg value="dummy"/>
  </bean>
  <bean id="appianAuthenticationProvider" class="com.appiancorp.suiteapi.security.auth.AuthenticationProviderWrapper">
    <constructor-arg ref="appianAuthenticationProviderInternal"/>
    <constructor-arg ref="scsKeyChangeHandler"/>
  </bean>

  <bean id="appianAuthenticationProviderInternal" class="com.appiancorp.security.auth.AppianAuthenticationProvider">
    <constructor-arg ref="compositeAuthenticationFilter" />
    <constructor-arg ref="compositeAuthenticator"/>
  </bean>

  <bean id="appianUserDetailsServiceForRememberMe" class="com.appiancorp.suiteapi.security.auth.AppianUserDetailsService">
    <constructor-arg value="false"/>
  </bean>

  <bean id="rememberMeScsHandler" class="com.appiancorp.security.auth.rememberme.RememberMeScsHandler">
    <constructor-arg ref="rememberMeSettings" />
  </bean>

  <bean id="appianRememberMeServices" class="com.appiancorp.security.auth.rememberme.AppianPersistentTokenBasedRememberMeServices">
    <constructor-arg ref="rememberMeSettings"/>
    <constructor-arg ref="appianUserDetailsServiceForRememberMe"/>
    <constructor-arg ref="rememberMeTokenRepository"/>
    <constructor-arg ref="rememberMeTokenValidator"/>
    <constructor-arg ref="rememberMeScsHandler" />
    <constructor-arg ref="portalAuthenticationDetailsSource"/>
    <constructor-arg ref="portalSessionAuthenticationStrategy"/>
    <constructor-arg ref="rememberMeDeferralStrategyEvaluator"/>
    <constructor-arg ref="featureToggleClient"/>
    <property name="seriesLength" value="32"/>
    <property name="tokenLength" value="32"/>
  </bean>

  <bean id="beanPostProcessorForAuthMgr" class="com.appiancorp.security.auth.BeanPostProcessorForAuthMgr">
    <property name="authenticationEventPublisher" ref="appianAuthenticationEventPublisher"/>
  </bean>

  <bean id="appianAuthenticationEventPublisher" class="com.appiancorp.security.auth.AppianAuthenticationEventPublisher"/>

</beans>
