<chapter xmlns="http://docbook.org/ns/docbook" version="5.0" xml:id="jaas">
    <info><title>Java Authentication and Authorization Service (JAAS) Provider</title></info>

    <section xml:id="jaas-overview">
        <info><title>Overview</title></info>
        <para>Spring Security provides a package able to delegate
            authentication requests to the Java Authentication and Authorization
            Service (JAAS). This package is discussed in detail below.</para>
        
        <para>Central to JAAS operation are login configuration files. To
            learn more about JAAS login configuration files, consult the JAAS
            reference documentation available from Sun Microsystems. We expect you
            to have a basic understanding of JAAS and its login configuration file
            syntax in order to understand this section.</para>
    </section>
    
    <section xml:id="jaas-config">
        <info><title>Configuration</title></info>
        <para>The <literal>JaasAuthenticationProvider</literal> attempts to
            authenticate a user’s principal and credentials through JAAS.</para>
        
        <para>Let’s assume we have a JAAS login configuration file,
            <literal>/WEB-INF/login.conf</literal>, with the following
            contents:
<programlisting>
JAASTest {
    sample.SampleLoginModule required;
};</programlisting></para>      
        <para>Like all Spring Security beans, the
            <classname>JaasAuthenticationProvider</classname> is configured via the
            application context. The following definitions would correspond to the
            above JAAS login configuration file:
<programlisting><![CDATA[
<bean id="jaasAuthenticationProvider"
   class="org.springframework.security.authentication.jaas.JaasAuthenticationProvider">
 <property name="loginConfig" value="/WEB-INF/login.conf"/>
 <property name="loginContextName" value="JAASTest"/>
 <property name="callbackHandlers">
  <list>
   <bean 
     class="org.springframework.security.authentication.jaas.JaasNameCallbackHandler"/>
   <bean 
     class="org.springframework.security.authentication.jaas.JaasPasswordCallbackHandler"/>
  </list>
  </property>
  <property name="authorityGranters">
    <list>
      <bean class="org.springframework.security.authentication.jaas.TestAuthorityGranter"/>
    </list>
  </property>
</bean> 
]]></programlisting></para>
        
        <para>The <literal>CallbackHandler</literal>s and
            <interfacename>AuthorityGranter</interfacename>s are discussed below.</para>
        
        <section xml:id="jaas-callbackhandler">
            <info><title xml:id="jaas-callback-handler">JAAS CallbackHandler</title></info>
            
            <para>Most JAAS <literal>LoginModule</literal>s require a callback
                of some sort. These callbacks are usually used to obtain the
                username and password from the user.</para>
            
            <para>In a Spring Security deployment, Spring Security is
                responsible for this user interaction (via the authentication
                mechanism). Thus, by the time the authentication request is
                delegated through to JAAS, Spring Security's authentication
                mechanism will already have fully-populated an
                <interfacename>Authentication</interfacename> object containing all the
                information required by the JAAS
                <literal>LoginModule</literal>.</para>
            
            <para>Therefore, the JAAS package for Spring Security provides two
                default callback handlers,
                <literal>JaasNameCallbackHandler</literal> and
                <literal>JaasPasswordCallbackHandler</literal>. Each of these
                callback handlers implement
                <literal>JaasAuthenticationCallbackHandler</literal>. In most cases
                these callback handlers can simply be used without understanding the
                internal mechanics.</para>
            
            <para>For those needing full control over the callback behavior,
                internally <literal>JaasAutheticationProvider</literal> wraps these
                <literal>JaasAuthenticationCallbackHandler</literal>s with an
                <literal>InternalCallbackHandler</literal>. The
                <literal>InternalCallbackHandler</literal> is the class that
                actually implements JAAS’ normal <literal>CallbackHandler</literal>
                interface. Any time that the JAAS <literal>LoginModule</literal> is
                used, it is passed a list of application context configured
                <literal>InternalCallbackHandler</literal>s. If the
                <literal>LoginModule</literal> requests a callback against the
                <literal>InternalCallbackHandler</literal>s, the callback is in-turn
                passed to the <literal>JaasAuthenticationCallbackHandler</literal>s
                being wrapped.</para>
        </section>
        
        <section xml:id="jaas-authoritygranter">
            <info><title xml:id="jaas-authority-granter">JAAS AuthorityGranter</title></info>
            
            <para>JAAS works with principals. Even "roles" are represented as
                principals in JAAS. Spring Security, on the other hand, works with
                <interfacename>Authentication</interfacename> objects. Each
                <interfacename>Authentication</interfacename> object contains a single
                principal, and multiple <interfacename>GrantedAuthority</interfacename>[]s. To
                facilitate mapping between these different concepts, Spring
                Security's JAAS package includes an
                <literal>AuthorityGranter</literal> interface.</para>
            
            <para>An <literal>AuthorityGranter</literal> is responsible for
                inspecting a JAAS principal and returning a set of 
                <literal>String</literal>s, representing the authorities assigned to the principal. 
                For each returned authority string, the
                <classname>JaasAuthenticationProvider</classname> creates a
                <classname>JaasGrantedAuthority</classname> (which implements Spring
                Security’s <interfacename>GrantedAuthority</interfacename> interface) containing
                the authority string and the JAAS principal that the
                <interfacename>AuthorityGranter</interfacename> was passed. The
                <classname>JaasAuthenticationProvider</classname> obtains the JAAS
                principals by firstly successfully authenticating the user’s
                credentials using the JAAS <literal>LoginModule</literal>, and then
                accessing the <literal>LoginContext</literal> it returns. A call to
                <literal>LoginContext.getSubject().getPrincipals()</literal> is
                made, with each resulting principal passed to each
                <interfacename>AuthorityGranter</interfacename> defined against the
                <literal>JaasAuthenticationProvider.setAuthorityGranters(List)</literal>
                property.</para>
            
            <para>Spring Security does not include any production
                <interfacename>AuthorityGranter</interfacename>s given that every JAAS principal
                has an implementation-specific meaning. However, there is a
                <literal>TestAuthorityGranter</literal> in the unit tests that
                demonstrates a simple <literal>AuthorityGranter</literal>
                implementation.</para>
        </section>
    </section>
</chapter>