views:

46

answers:

2

I'm using tomcat 6, spring mvc 3.0.0 and spring security 3.0.0, and since the passwords I store in the database are sha1 hashed, I can't use digest authentication (section 9.2.1 of the documentation spells that out). For this reason, I need to make authentication happen through https.

Due to potential processing overhead, I want to keep as much of the traffic in regular http as possible. Is there a way I can make spring use https for unathenticated requests, then use http once authentication is done? I think this is done with a ChannelProcessingFilter of some sort, but I'm stumped as to the particulars.

Here's my application-security.xml file as it currently stands:

<beans:beans xmlns="http://www.springframework.org/schema/security"
    xmlns:beans="http://www.springframework.org/schema/beans"
    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-3.0.xsd
                        http://www.springframework.org/schema/security http://www.springframework.org/schema/security/spring-security-3.0.xsd"&gt;

    <http use-expressions="true">
        <intercept-url pattern="/**" access="isAuthenticated()" />
        <http-basic />
    </http>

    <authentication-manager>
        <authentication-provider user-service-ref="myUserDetailsService">
            <password-encoder hash="sha"/>
        </authentication-provider>
    </authentication-manager>

    <beans:bean id="myUserDetailsService"
        class="path.to.myUserDetailsServiceImpl">
    </beans:bean>

</beans:beans>

Thanks for the help.

+3  A: 

If at any point you pass a session id over HTTP you are violating OWASP A9. An attacker doesn't need the password if he has the session id. I would not implement this feature in your application, https is very light weight and I think you should look into saving resources in places that doesn't mean that your clients will be hacked.

Rook
+1  A: 

Not sure exactly how to do it using Spring MVC but I did accomplish this using Grails with Spring Security 3...if you are interested you can see my blog post here.

Because that will not really help you...I did a quick google search and found this post which looks correct and says to configure your web.xml:

<context-param>
    <param-name>contextConfigLocation</param-name>
    <param-value>
        /WEB-INF/applicationContext-security.xml
    </param-value>
</context-param>

     <filter>
    <filter-name>springSecurityFilterChain</filter-name>
    <filter-class>org.springframework.web.filter.DelegatingFilterProxy</filter-class>
</filter>
<filter-mapping>
    <filter-name>springSecurityFilterChain</filter-name>
    <url-pattern>/*</url-pattern>
</filter-mapping>

and your applicationContext-security.xml as such:

  <beans:beans xmlns="http://www.springframework.org/schema/security"
    xmlns:beans="http://www.springframework.org/schema/beans" 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-2.0.xsd
                        http://www.springframework.org/schema/security http://www.springframework.org/schema/security/spring-security-2.0.1.xsd"&gt;

    <http>
        <intercept-url pattern="/url1.htm"
        access="IS_AUTHENTICATED_ANONYMOUSLY" requires-channel="https" />
        <intercept-url pattern="/url2.htm"
        access="IS_AUTHENTICATED_ANONYMOUSLY" requires-channel="https" />
        <intercept-url pattern="/**"
        access="IS_AUTHENTICATED_ANONYMOUSLY" requires-channel="http" />

        <anonymous />
        <http-basic/>
    </http>

    <!-- This bean is optional; it isn't used by any other bean as it only listens and logs -->
    <beans:bean id="loggerListener" class="org.springframework.security.event.authentication.LoggerListener"/>

</beans:beans>

Also take a look at this site for more info and how to configure tomcats SSL connector.

Eric W