Hi Patrick,

I just finished (10 mins ago) implementing my Spring Security service
over the top of the Requestfactory.

I am sure there are some holes (not security ones, just stuff I have
missed) but here is what I did.
I have a user entity (that represents the user). this entity has the
username, and the password.

@Entity
@Configurable
public class IsuproUser {

    private String username;

    private String password;

    @OneToOne
    private Person person;

    // clear or sha256
    private String passwordEncoding;

    private boolean enabled;
}

/* and example table insert for a user then looks like
INSERT INTO isupro_user (password, username,person, enabled,
password_encoding) VALUES
('5e884898da28047151d0e56f8dc6292773603d0d6aabbdd62a11ef721d1542d8','rbuckland',
1, 1, 'sha256')
sha256 value is 'password'.

echo -n password | sha256sum

*/


I have a fairly clean META-INF/spring/applicationContext-security.xml
file.

<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";>

        <!-- HTTP security configurations -->
  <http auto-config="true" use-expressions="true">
    <form-login login-processing-url="/resources/
j_spring_security_check"
                login-page="/login.jspx"
                authentication-failure-url="/login.jspx?
login_error=t" />
    <logout logout-url="/resources/j_spring_security_logout" />

    <!-- Configure these elements to secure URIs in your application --
>
    <intercept-url pattern="/admin/**" access="hasRole('ROLE_ADMIN')" /
>
    <intercept-url pattern="/gwtRequest/**"
access="isAuthenticated()" />
    <intercept-url pattern="/isupro.jsp" access="isAuthenticated()" />
    <intercept-url pattern="/**" access="permitAll" />

  </http>

  <beans:bean
class="org.springframework.security.authentication.encoding.ShaPasswordEncoder"
id="passwordEncoder">
    <beans:constructor-arg value="256" />
  </beans:bean>

  <beans:bean id="myUserDetailsService"
class="isupro.security.IsuproUserDetailsService" />

        <!-- Configure Authentication mechanism -->
  <authentication-manager alias="authenticationManager">
    <authentication-provider user-service-ref="myUserDetailsService">
      <password-encoder ref="passwordEncoder" />
    </authentication-provider>
  </authentication-manager>

</beans:beans>


So I have (hopefully) secured the app, on the isupro.jsp (this is the
GWT bootstrap).

I have a UserDetails class. Which is just a minor extension on the
spring one (seems there is some depecation for this "User" class.. but
I moved on :-) worry about that later ).

public class IsuproUserDetails extends User {

    private IsuproUser isuproUser;

    private static final long serialVersionUID = 1L;

    @SuppressWarnings("deprecation")
    public IsuproUserDetails(IsuproUser isuproUser) {
        super(isuproUser.getUsername(), isuproUser.getPassword(),
isuproUser.getEnabled(),true, true, true, getAuthorities(false));
        this.setIsuproUser(isuproUser);
    }

    // threading issue here .. change
    private static GrantedAuthority[] getAuthorities(boolean isAdmin)
{
        List<GrantedAuthority> authList = new
ArrayList<GrantedAuthority>(2);
        authList.add(new GrantedAuthorityImpl("ROLE_USER"));
        if (isAdmin) {
            authList.add(new GrantedAuthorityImpl("ROLE_ADMIN"));
        }
        return authList.toArray(new GrantedAuthority[] {});
    }

    public void setIsuproUser(IsuproUser isuproUser) {
        this.isuproUser = isuproUser;
    }

    public IsuproUser getIsuproUser() {
        return isuproUser;
    }

}

Now we have two more classes to care about. first, the one that
SpringSecurity needs, the UserDetails service. I use JPA (it was an
app based off ROO (side note: I find ROO cumbersome! :-/ )


public class IsuproUserDetailsService implements UserDetailsService {

    @Override
    public UserDetails loadUserByUsername(String username) throws
UsernameNotFoundException, DataAccessException {
        IsuproUser isuproUser =
IsuproUser.findUserByUsername(username);
        if (isuproUser != null) {
            return new IsuproUserDetails(isuproUser);
        } else {
            throw new UsernameNotFoundException("Username : " +
username + " : was not found");
        }
    }

}

And then the one that the GWT RequestFactory needs.

public class IsuproUserInformation extends UserInformation {

    public IsuproUserInformation(String redirectUrl) {
        super(redirectUrl);
    }

    @Override
    public String getEmail() {
        return "[email protected]";
    }

    @Override
    public Long getId() {
        if
(SecurityContextHolder.getContext().getAuthentication().isAuthenticated())
{
            IsuproUserDetails userdetails = (IsuproUserDetails)
SecurityContextHolder.getContext().getAuthentication().getPrincipal();
            return userdetails.getIsuproUser().getId();
        } else {
            return -1L;
        }
    }

    @Override
    public String getLoginUrl() {
        return "/login.jspx";
    }

    @Override
    public String getLogoutUrl() {

        return "/logout";
    }

    @Override
    public String getName() {
        if
(SecurityContextHolder.getContext().getAuthentication().isAuthenticated())
{
            IsuproUserDetails userdetails = (IsuproUserDetails)
SecurityContextHolder.getContext().getAuthentication().getPrincipal();
            return userdetails.getIsuproUser().getUsername(); // this
could be the name of the getPerson()
        } else {
            return "Guest";
        }

    }

    @Override
    public boolean isUserLoggedIn() {
        return
SecurityContextHolder.getContext().getAuthentication().isAuthenticated();
    }

    @Override
    public void setId(Long id) {
        // we don't allow setting the ID
    }

}


And finally, telling the GWT Requestfactory about this UserInformation
class.

  <servlet>
    <servlet-name>requestFactory</servlet-name>
    <servlet-
class>com.google.gwt.requestfactory.server.RequestFactoryServlet</
servlet-class>
    <init-param>
      <param-name>userInfoClass</param-name>
      <param-value>isupro.security.IsuproUserInformation</param-value>
    </init-param>
  </servlet>

So now, If i navigate to /isupro.jsp, it pushes me to /login.jspx. I
login with the username/password(database has an encrypted sha256
value of the password and spring does the magic of sha-ing the
password for comparison.

A nice tutorial (for others to read is here).
http://www.packtpub.com/article/spring-security-configuring-secure-passwords


This is what it looks like in GWT to pull that user up. (Straight from
Spring ROO).

        /*
         * identify the logged in user
         */
        Receiver<UserInformationProxy> receiver = new
Receiver<UserInformationProxy>() {
            public void onSuccess(UserInformationProxy
userInformationProxy) {
 
shell.getLoginWidget().setUserInformation(userInformationProxy);
            }
        };
 
requestFactory.userInformationRequest().getCurrentUserInformation(Window.Location.getHref()).fire(receiver);


That is it.

HTH
Ramon Buckland

On Nov 12, 1:32 pm, Patrick Hilsbos <[email protected]>
wrote:
> Hi,
> could you get a bit more in detail, how to implement the auth - e.g. where to 
> store the authcode?
> Do i have to create a session on my own...?
>
> I already went through a couple of projects dealing with spring security / 
> acegi.
>
> Thanks !!!
>
> On 10.11.2010, at 17:57, Jack wrote:
>
> > Everytime a request is made the RequestFactoryServlet loads an
> > implementation of UserInformation and calls boolean isUserLoggedIn().
> > If you do not provide a custom UserInformation implementation a
> > SimpleUserInformationImpl will be choosen which always returns true
> > for isUserLoggedIn().
>
> > To define a custom UserInformation implementation you need to add to
> > your web.xml something like this:
>
> > <servlet>
> >  <servlet-name>requestFactoryServlet</servlet-name>
> >  <servlet-
> > class>com.google.gwt.requestfactory.server.RequestFactoryServlet</
> > servlet-class>
> >  <init-param>
> >     <param-name>userInfoClass</param-name>
> >     <param-value>your.example.YourUserInformationImpl</param-value>
> >  </init-param>
> > </servlet>
>
> > With your own UserInformation implementation you can check if an user
> > is logged in. Inside the isUserLoggedIn() method you can access the
> > HttpServletRequest object via
>
> > HttpServletRequest request =
> > RequestFactoryServlet.getThreadLocalRequest();
>
> > Now you should have anything you need to authenticate the request
> > (request cookies, request headers, request session).
>
> > To do the actual login and logout of an user I would use a normal GWT
> > RemoteService with two methods
>
> > String login(String user, String password)
> > void logout(String authtoken)
>
> > On 9 Nov., 20:16, "Max E." <[email protected]> wrote:
> >> Hello,
>
> >> I'm having problems to understand how User Authentication works with
> >> the RequestFactory.
> >> I do understand the documentation and the expenses example.
>
> >> How is it possible to implement Authentication/ How do users login?
> >> How can Users only view the Entities they are allowed to see.
> >> How can the Server verify that they can only change/persist entities
> >> they are allowed to change?
>
> >> I did not find any tutorial or documentation about this. The only
> >> thing I found was UserInformation and RequestSecurityProvider in GWT.
>
> >> Can somebody explain this?
>
> > --
> > You received this message because you are subscribed to the Google Groups 
> > "Google Web Toolkit" group.
> > To post to this group, send email to [email protected].
> > To unsubscribe from this group, send email to 
> > [email protected].
> > For more options, visit this group 
> > athttp://groups.google.com/group/google-web-toolkit?hl=en.
>
>

-- 
You received this message because you are subscribed to the Google Groups 
"Google Web Toolkit" group.
To post to this group, send email to [email protected].
To unsubscribe from this group, send email to 
[email protected].
For more options, visit this group at 
http://groups.google.com/group/google-web-toolkit?hl=en.

Reply via email to