Pathway from ACEGI to Spring Security 2.0(3)

  1. OK, so now we have setup the database based resources and now the next step is to get Spring Security to read the user details from the database. The examples that come with Spring Security 2.0 shows you how to keep a list of users and authorities in the configuration file like this:
    1. <authentication-provider>  
    2.     <user-service>  
    3.     <user name="rod" password="password" authorities="ROLE_SUPERVISOR, ROLE_USER" />  
    4.     <user name="dianne" password="password" authorities="ROLE_USER,ROLE_TELLER" />  
    5.     <user name="scott" password="password" authorities="ROLE_USER" />  
    6.     <user name="peter" password="password" authorities="ROLE_USER" />  
    7.     </user-service>  
    8. </authentication-provider>  
    You could replace these examples with this configuration so that you can read the user details straight from the database like this:
    1. <authentication-provider>  
    2.     <jdbc-user-service data-source-ref="dataSource" />  
    3. </authentication-provider>  
    While this is a very fast and easy way to configure database based security it does mean that you have to conform to a default databases schema. By default, the <jdbc-user-service> requires the following tables: user, authorities, groups, group_members and group_authorities.
    In my case this was not going to work as my security schema it not the same as what the <jdbc-user-service> requires, so I was forced to change the <authentication-provider>:
    1. <authentication-provider>  
    2.     <jdbc-user-service data-source-ref="dataSource"  
    3.     users-by-username-query="SELECT U.username, U.password, U.accountEnabled AS 'enabled' FROM User U where U.username=?"  
    4.     authorities-by-username-query="SELECT U.username, R.name as 'authority' FROM User U JOIN Authority A ON u.id = A.userId JOIN Role R ON R.id = A.roleId WHERE U.username=?"/>  
    5. </authentication-provider>  
    By adding the users-by-username-query and authorities-by-username-query properties you are able to override the default SQL statements with your own. As in ACEGI security you must make sure that the columns that your SQL statement returns is the same as what Spring Security expects. There is a another property group-authorities-by-username-query which I am not using and have therefore left it out of this example, but it works in exactly the same manner as the other two SQL statements.

    This feature of the <jdbc-user-service> has only been included in the past month or so and was not available in the pre-release versions of Spring Security. Luckily it has been added as it does make life a lot easier. You can read about this here and here.

    The dataSource bean instructs which database to connect to, it is not included in my configuration file as it's not specific to security. Here is an example of a dataSource bean for those who are not sure:
    1. <bean id="dataSource" class="org.springframework.jdbc.datasource.DriverManagerDataSource">  
    2.     <property name="driverClassName" value="com.mysql.jdbc.Driver"/>  
    3.     <property name="url" value="jdbc:mysql://localhost/db_name?useUnicode=true&characterEncoding=utf-8"/>  
    4.     <property name="username" value="root"/>  
    5.     <property name="password" value="pwd"/>  
    6. </bean>  
  2. And that is all for the configuration of Spring Security. My last task was to change my current logon screen. In ACEGI you could create your own logon <form> by making sure that you POSTED the correctly named HTML input elements to the correct URL. While you can still do this in Spring Security 2.0, some of the names have changed.
    You can still call your username field j_username and your password field j_password as before.
    1. <input type="text" name="j_username" id="j_username"/>  
    2. <input type="password" name="j_password" id="j_password"/>  
    However you must set the action property of your <form> to point to j_spring_security_check and not j_acegi_security_check.
    1. <form method="post" id="loginForm" action="<c:url value='j_spring_security_check'/>"  
    There are a few places in our application where the user can logout, this is a link that redirects the logout request to the security framework so that it can be handled accordingly. This needs to be changed from j_acegi_logout to j_spring_security_logout.
    1. <a href='<c:url value="j_spring_security_logout"/>'>Logout</a>  

Conclusion

This short guide on how to configure Spring Security 2.0 with access to resources stored in a database does not come close to illustrating the host of new features that are available in Spring Security 2.0, however I think that it does show some of the most commonly used abilities of the framework and I hope that you will find it useful.

One of the benefits of Spring Security 2.0 over ACEGI is the ability to write more consice configuration files, this is clearly shown when I compare my old ACEGI configration (172 lines) file to my new one (42 lines).
Here is my complete securityContext.xml file:

  1. <?xml version="1.0" encoding=
posted @ 2008-11-20 08:56  Earl_86  阅读(330)  评论(0编辑  收藏  举报