Bonjour,
Contexte:
- CXF 2.2.7
- Spring framework 2.5.6
- Spring security 2.0.5
- Tomcat 6.0.20
Je veux sécuriser un service web avec Spring Security en utilisant deux autentication provider:
....
<security:http create-session="never" realm="monRealm">
<security:intercept-url pattern="/**" access="ROLE_TECHNICAL"/>
<security:http-basic>
<security:anonymous/>
</security:http>
<security:authentication-manager alias="authenticationManager" />
<bean id="technicalAuthenticationProvider" class="org.springframework.security.providers.dao. DaoAuthenticationProvider>
<security:custom-authentication-provider />
<property name="userDetailsService">
<ref bean="technicalUserDetailservice" />
</property>
</bean>
<bean id="technicalUserDetailservice" class="monpackage.TechnicalUserDetailsImpl"
</bean>
<bean id="businessAuthenticationProvider" class="org.springframework.security.providers.dao. DaoAuthenticationProvider>
<security:custom-authentication-provider />
<property name="userDetailsService">
<ref bean="userDetailsService" />
</property>
</bean>
....
La classe monpackage.TechnicalUserDetailsImpl est une implémentation de UserDetailService.loadUserByUsername(String login):UserDetails.
Le premier (technicalAuthenticationProvider) sert à authentifier un user technique stocké dans le Basic Auth de la requête HTTP et le second (businessAuthenticationProvider) sert à autentifier un user applicatif (stocké dans l'entête UNT du message SOAP). J'ai le contrôle du premier, mais pas du second.
Le processus d'authentification se déroule dans l'ordre suivant:
1- Authentification du user technique Basic Auth de la requête HTTP par le filtre de Spring Security <security:http-basic>
2- Authentification du user applicatif par un intercepteur CXF (qui se charge de me décortiquer le jeton UNT) dans lequel j'injecte le bean authenticationManager pour authentifier le jeton:
...
Authentication auth=new UsernamePasswordAuthentication(user,pass);
auth=auth.authenticate(auth);
....
Pour certainnes opérations du web service, j'utilise l'utlisateur anonyme comme utilisateur applicatif. Comme je n'ai pas le controle du fournisseur businessAuthenticationProvider, je stocke mon user anonyme (anonymousUser,ROLE_ANONYMOUS) dans le fournisseur technicalAuthenticationProvider.
Le problème:
Lorsque j'exécute le service web avec un utilisateur anonyme:
1- le filtre Spring Security <security:http-basic> authentifie correctement le user technique.
2- l'intercepteur authentifie l'utilisateur anaonyme via le fournisseur technicalAuthenticationProvider et essaye quand même de le réauthentifier via le fournisseur businessAuthenticationProvider !!!
Normalement il est dit dans la javadoc du ProviderManager la chose suivante:
AuthenticationProviders are usually tried in order until one provides a non-null response. A non-null response indicates the provider had authority to decide on the authentication request and no further providers are tried.
Donc normalement, si le fournisseur technicalAuthenticationProvider retourne l'utilisateur anonyme, l'AuthenticationProviders devrait s'en contenter. Mais non, il essaye quand même de récupérer le user anonyme auprès du businessAuthenticationProvider !!!
Aussi, j'ai vérifié que l'utilisateur anonyme est bien rensegné dans le UserDetails retourné par la méthode TechnicalUserDetailsImpl.loadUserByUsername(String login)
Si qq à une idée, merci de partager![]()
Partager