# Anonymous Authentication

## Overview

Particularly in the case of web request URI security, sometimes it is more convenient to assign configuration attributes against every possible secure object invocation. Put differently, sometimes it is nice to say `ROLE_SOMETHING` is required by default and only allow certain exceptions to this rule, such as for login, logout and home pages of an application. There are also other situations where anonymous authentication would be desired, such as when an auditing interceptor queries the SecurityContextHolder to identify which principal was responsible for a given operation. Such classes can be authored with more robustness if they know the SecurityContextHolder always contains an Authentication object, and never `null`.

## Configuration

Spring Security provides three classes that together provide an anonymous authentication feature. `AnonymousAuthenticationToken` is an implementation of Authentication, and stores the GrantedAuthority[]s which apply to the anonymous principal. There is a corresponding `AnonymousAuthenticationProvider`, which is chained into the `ProviderManager` so that `AnonymousAuthenticationTokens` are accepted. Finally, there is an AnonymousProcessingFilter, which is chained after the normal authentication mechanisms and automatically add an `AnonymousAuthenticationToken` to the SecurityContextHolder if there is no existing Authentication held there. The definition of the filter and authentication provider appears as follows:

    <bean id="anonymousProcessingFilter"
        class="org.springframework.security.providers.anonymous.AnonymousProcessingFilter">
      <property name="key" value="foobar"/>
      <property name="userAttribute" value="anonymousUser,ROLE_ANONYMOUS"/>
    </bean>

    <bean id="anonymousAuthenticationProvider"
        class="org.springframework.security.providers.anonymous.AnonymousAuthenticationProvider">
      <property name="key" value="foobar"/>
    </bean>

The `key` is shared between the filter and authentication provider, so that tokens created by the former are accepted by the latter. The `userAttribute` is expressed in the form of `usernameInTheAuthenticationToken,grantedAuthority[,grantedAuthority]`. This is the same syntax as used after the equals sign for `InMemoryDaoImpl`'s `userMap` property.

As explained earlier, the benefit of anonymous authentication is that all URI patterns can have security applied to them. For example:

    <bean id="filterInvocationInterceptor"
        class="org.springframework.security.intercept.web.FilterSecurityInterceptor">
      <property name="authenticationManager" ref="authenticationManager"/>
      <property name="accessDecisionManager" ref="httpRequestAccessDecisionManager"/>
      <property name="objectDefinitionSource">
        <security:filter-invocation-definition-source>
          <security:intercept-url pattern='/index.jsp' access='ROLE_ANONYMOUS,ROLE_USER'/>
          <security:intercept-url pattern='/hello.htm' access='ROLE_ANONYMOUS,ROLE_USER'/>
          <security:intercept-url pattern='/logoff.jsp' access='ROLE_ANONYMOUS,ROLE_USER'/>
          <security:intercept-url pattern='/login.jsp' access='ROLE_ANONYMOUS,ROLE_USER'/>
          <security:intercept-url pattern='/**' access='ROLE_USER'/>
        </security:filter-invocation-definition-source>" +
      </property>
    </bean>

Rounding out the anonymous authentication discussion is the `AuthenticationTrustResolver` interface, with its corresponding `AuthenticationTrustResolverImpl` implementation. This interface provides an `isAnonymous(Authentication)` method, which allows interested classes to take into account this special type of authentication status. The ExceptionTranslationFilter uses this interface in processing `AccessDeniedException`s. If an `AccessDeniedException` is thrown, and the authentication is of an anonymous type, instead of throwing a 403 (forbidden) response, the filter will instead commence the AuthenticationEntryPoint so the principal can authenticate properly. This is a necessary distinction, otherwise principals would always be deemed "authenticated" and never be given an opportunity to login via form, basic, digest or some other normal authentication mechanism