Issue
I am upgrading spring security (and many other spring libraries) from version 3 to version 4 using this https://github.com/spring-projects/spring-security-migrate-3-to-4/compare/xml?expand=1 commit as a reference.
When the application server (tomcat) starts, several errors regarding to spring appears:
org.springframework.beans.factory.BeanCreationException: Error creating bean with name 'org.springframework.security.filterChains': Cannot resolve reference to bean 'org.springframework.security.web.DefaultSecurityFilterChain#0' while setting bean property 'sourceList' with key [0]; nested exception is org.springframework.beans.factory.BeanCreationException: Error creating bean with name 'org.springframework.security.web.DefaultSecurityFilterChain#0': Cannot resolve reference to bean 'org.springframework.security.web.access.intercept.FilterSecurityInterceptor#0' while setting constructor argument with key [8]; nested exception is org.springframework.beans.factory.BeanCreationException: Error creating bean with name 'org.springframework.security.web.access.intercept.FilterSecurityInterceptor#0': Invocation of init method failed; nested exception is java.lang.IllegalArgumentException: Unsupported configuration attributes: [hasRole('SUPERADMIN'), hasRole('ADMIN'), hasRole('USER'), permitAll]
Here is my spring-security.xml file:
<beans xmlns="http://www.springframework.org/schema/beans"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xmlns:sec="http://www.springframework.org/schema/security"
xsi:schemaLocation="
http://www.springframework.org/schema/beans http://www.springframework.org/schema/beans/spring-beans-4.1.xsd
http://www.springframework.org/schema/security http://www.springframework.org/schema/security/spring-security-4.0.xsd">
<import resource="businessContext.xml"/>
<!-- Spring security configs -->
<bean id="valuUserDetailsService" class="com.xxx.business.remote.ValuUserDetailsService">
<property name="userService" ref="userService"/>
</bean>
<bean id="valuPasswordEncoderService" class="com.xxx.business.remote.ValuPasswordEncoderService">
</bean>
<bean id="daoAuthenticationProvider" class="org.springframework.security.authentication.dao.DaoAuthenticationProvider">
<property name="userDetailsService" ref="valuUserDetailsService"/>
<property name="passwordEncoder" ref="valuPasswordEncoderService"/>
</bean>
<sec:authentication-manager>
<sec:authentication-provider ref="daoAuthenticationProvider"/>
</sec:authentication-manager>
<!-- Note: use IS_AUTHENTICATED_ANONYMOUSLY for any target that is allowed to be accessed anonymously. The patterns are matched in the listed order. -->
<sec:http disable-url-rewriting="false" use-expressions="false" create-session="always">
<sec:headers disabled="true"/>
<sec:csrf disabled="true"/>
<sec:intercept-url pattern="/remoteservices/superadmin/**" access="hasRole('SUPERADMIN')"/>
<sec:intercept-url pattern="/remoteservices/admin/**" access="hasRole('ADMIN')"/>
<sec:intercept-url pattern="/remoteservices/**" access="permitAll"/>
<sec:intercept-url pattern="/rest/401" access="permitAll"/>
<sec:intercept-url pattern="/rest/**" access="hasRole('USER')"/>
<sec:http-basic/>
</sec:http>
</beans>
It has a little modifications after the library upgrade but otherwise this same file worked with spring 3. Any ideas what would be wrong?
Solution
By explicitly setting use-expressions="false"
you are disabling the use of expressions in the 'access' attributes in <intercept-url>.
Since hasRole('SUPERADMIN')
, permitAll
etc are expressions, there is an exception thrown saying that they are unsupported.
You can either set use-expressions
to true
, which is the default, or change the rule to state <sec:intercept-url pattern="/remoteservices/superadmin/**" access="ROLE_SUPERADMIN"/>
.
This is described in detail in the Migrate <http> section of the migration guide.
Note that Spring Security 4 has reached its end of life since October 2020. I would advise you to migrate to a supported version of Spring Security 5 as soon as possible.
Answered By - Eleftheria Stein-Kousathana