Package nu.localhost.tapestry5.springsecurity.services

Source Code of nu.localhost.tapestry5.springsecurity.services.SecurityModule

/*
* Copyright 2007 Ivan Dubrov
* Copyright 2007, 2008, 2009 Robin Helgelin
* Copyright 2009 Michael Gerzabek
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
*     http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/

package nu.localhost.tapestry5.springsecurity.services;

import java.util.Collection;
import java.util.LinkedHashMap;
import java.util.List;

import javax.servlet.ServletException;
import javax.servlet.http.HttpServletRequest;

import nu.localhost.tapestry5.springsecurity.services.internal.HttpServletRequestFilterWrapper;
import nu.localhost.tapestry5.springsecurity.services.internal.LogoutServiceImpl;
import nu.localhost.tapestry5.springsecurity.services.internal.RequestFilterWrapper;
import nu.localhost.tapestry5.springsecurity.services.internal.SaltSourceImpl;
import nu.localhost.tapestry5.springsecurity.services.internal.SecurityChecker;
import nu.localhost.tapestry5.springsecurity.services.internal.SpringSecurityExceptionTranslationFilter;
import nu.localhost.tapestry5.springsecurity.services.internal.SpringSecurityWorker;
import nu.localhost.tapestry5.springsecurity.services.internal.StaticSecurityChecker;
import nu.localhost.tapestry5.springsecurity.services.internal.T5AccessDeniedHandler;
import nu.localhost.tapestry5.springsecurity.services.internal.TapestryLogoutHandler;

import org.apache.tapestry5.ioc.Configuration;
import org.apache.tapestry5.ioc.MappedConfiguration;
import org.apache.tapestry5.ioc.OrderedConfiguration;
import org.apache.tapestry5.ioc.ServiceBinder;
import org.apache.tapestry5.ioc.annotations.Contribute;
import org.apache.tapestry5.ioc.annotations.Inject;
import org.apache.tapestry5.ioc.annotations.InjectService;
import org.apache.tapestry5.ioc.annotations.Marker;
import org.apache.tapestry5.ioc.annotations.Primary;
import org.apache.tapestry5.ioc.annotations.Value;
import org.apache.tapestry5.ioc.internal.util.TapestryException;
import org.apache.tapestry5.ioc.services.ServiceOverride;
import org.apache.tapestry5.services.HttpServletRequestFilter;
import org.apache.tapestry5.services.LibraryMapping;
import org.apache.tapestry5.services.RequestFilter;
import org.apache.tapestry5.services.RequestGlobals;
import org.apache.tapestry5.services.transform.ComponentClassTransformWorker2;
import org.springframework.security.access.AccessDecisionManager;
import org.springframework.security.access.AccessDecisionVoter;
import org.springframework.security.access.ConfigAttribute;
import org.springframework.security.access.vote.AffirmativeBased;
import org.springframework.security.access.vote.RoleVoter;
import org.springframework.security.authentication.AnonymousAuthenticationProvider;
import org.springframework.security.authentication.AuthenticationManager;
import org.springframework.security.authentication.AuthenticationProvider;
import org.springframework.security.authentication.AuthenticationTrustResolver;
import org.springframework.security.authentication.AuthenticationTrustResolverImpl;
import org.springframework.security.authentication.ProviderManager;
import org.springframework.security.authentication.RememberMeAuthenticationProvider;
import org.springframework.security.authentication.dao.DaoAuthenticationProvider;
import org.springframework.security.core.userdetails.UserDetailsService;
import org.springframework.security.core.userdetails.memory.UserAttribute;
import org.springframework.security.core.userdetails.memory.UserAttributeEditor;
import org.springframework.security.crypto.password.PasswordEncoder;
import org.springframework.security.crypto.password.StandardPasswordEncoder;
import org.springframework.security.web.AuthenticationEntryPoint;
import org.springframework.security.web.access.intercept.DefaultFilterInvocationSecurityMetadataSource;
import org.springframework.security.web.access.intercept.FilterSecurityInterceptor;
import org.springframework.security.web.authentication.AnonymousAuthenticationFilter;
import org.springframework.security.web.authentication.LoginUrlAuthenticationEntryPoint;
import org.springframework.security.web.authentication.RememberMeServices;
import org.springframework.security.web.authentication.SavedRequestAwareAuthenticationSuccessHandler;
import org.springframework.security.web.authentication.SimpleUrlAuthenticationFailureHandler;
import org.springframework.security.web.authentication.UsernamePasswordAuthenticationFilter;
import org.springframework.security.web.authentication.logout.LogoutHandler;
import org.springframework.security.web.authentication.logout.SecurityContextLogoutHandler;
import org.springframework.security.web.authentication.rememberme.RememberMeAuthenticationFilter;
import org.springframework.security.web.authentication.rememberme.TokenBasedRememberMeServices;
import org.springframework.security.web.context.SecurityContextPersistenceFilter;
import org.springframework.security.web.servletapi.SecurityContextHolderAwareRequestFilter;
import org.springframework.security.web.util.matcher.RequestMatcher;

/**
* This module is automatically included as part of the Tapestry IoC Registry,
*
* @author Ivan Dubrov
* @author Robin Helgelin
* @author Michael Gerzabek
*/
public class SecurityModule {

    @SuppressWarnings( "unchecked" )
    public static void bind( final ServiceBinder binder ) {

        binder.bind( LogoutService.class, LogoutServiceImpl.class ).withMarker( SpringSecurityServices.class );
        binder.bind( AuthenticationTrustResolver.class, AuthenticationTrustResolverImpl.class ).withMarker(
                SpringSecurityServices.class );
        binder.bind( PasswordEncoder.class, StandardPasswordEncoder.class ).withMarker( SpringSecurityServices.class );
    }

   
    @Contribute(ServiceOverride.class)
    public static void setupApplicationServiceOverrides(MappedConfiguration<Class<?>,Object> configuration,
            @SpringSecurityServices SaltSourceService saltSource,
            @SpringSecurityServices UsernamePasswordAuthenticationFilter authenticationProcessingFilter) {
      configuration.add(SaltSourceService.class, saltSource);
      configuration.add(UsernamePasswordAuthenticationFilter.class, authenticationProcessingFilter);
    }
   
   
    @Marker( SpringSecurityServices.class )
    public static SaltSourceService buildSaltSource(
            @Inject @Value( "${spring-security.password.salt}" ) final String salt ) throws Exception {

        SaltSourceImpl saltSource = new SaltSourceImpl();
        saltSource.setSystemWideSalt( salt );
        saltSource.afterPropertiesSet();
        return saltSource;
    }

    public static void contributeFactoryDefaults( final MappedConfiguration<String, String> configuration ) {

        configuration.add( "spring-security.check.url", "/j_spring_security_check" );
        configuration.add( "spring-security.failure.url", "/loginfailed" );
        configuration.add( "spring-security.target.url", "/" );
        configuration.add( "spring-security.afterlogout.url", "/" );
        configuration.add( "spring-security.accessDenied.url", "" );
        configuration.add( "spring-security.force.ssl.login", "false" );
        configuration.add( "spring-security.rememberme.key", "REMEMBERMEKEY" );
        configuration.add( "spring-security.loginform.url", "/loginpage" );
        configuration.add( "spring-security.anonymous.key", "spring_anonymous" );
        configuration.add( "spring-security.anonymous.attribute", "anonymous,ROLE_ANONYMOUS" );
        configuration.add( "spring-security.password.salt", "DEADBEEF" );
        configuration.add( "spring-security.always.use.target.url", "false" );
    }

    @Contribute(ComponentClassTransformWorker2.class)
    @Primary
    public static void addSpringSecurityWorker(
            OrderedConfiguration<ComponentClassTransformWorker2> configuration,
            SecurityChecker securityChecker ) {

        configuration.add( "SpringSecurity", new SpringSecurityWorker( securityChecker ), "after:CleanupRender" );
    }

    public static void contributeHttpServletRequestHandler(
            OrderedConfiguration<HttpServletRequestFilter> configuration,
            @InjectService( "HttpSessionContextIntegrationFilter" ) HttpServletRequestFilter httpSessionContextIntegrationFilter,
            @InjectService( "AuthenticationProcessingFilter" ) HttpServletRequestFilter authenticationProcessingFilter,
            @InjectService( "RememberMeProcessingFilter" ) HttpServletRequestFilter rememberMeProcessingFilter,
            @InjectService( "SecurityContextHolderAwareRequestFilter" ) HttpServletRequestFilter securityContextHolderAwareRequestFilter,
            @InjectService( "AnonymousProcessingFilter" ) HttpServletRequestFilter anonymousProcessingFilter,
            @InjectService( "FilterSecurityInterceptor" ) HttpServletRequestFilter filterSecurityInterceptor,
            @InjectService( "SpringSecurityExceptionFilter" ) SpringSecurityExceptionTranslationFilter springSecurityExceptionFilter ) {

        configuration.add(
                "springSecurityHttpSessionContextIntegrationFilter",
                httpSessionContextIntegrationFilter,
                "before:ResteasyRequestFilter","before:springSecurity*" );
        configuration.add( "springSecurityAuthenticationProcessingFilter", authenticationProcessingFilter );
        configuration.add( "springSecurityRememberMeProcessingFilter", rememberMeProcessingFilter );
        configuration.add(
                "springSecuritySecurityContextHolderAwareRequestFilter",
                securityContextHolderAwareRequestFilter,
                "after:springSecurityRememberMeProcessingFilter" );
        configuration.add(
                "springSecurityAnonymousProcessingFilter",
                anonymousProcessingFilter,
                "after:springSecurityRememberMeProcessingFilter",
                "after:springSecurityAuthenticationProcessingFilter" );
        configuration.add( "springSecurityExceptionFilter", new HttpServletRequestFilterWrapper(
                springSecurityExceptionFilter ), "before:springSecurityFilterSecurityInterceptor" );
        configuration.add(
                "springSecurityFilterSecurityInterceptor",
                filterSecurityInterceptor,
                "after:springSecurity*" );
    }

    @Marker( SpringSecurityServices.class )
    public static HttpServletRequestFilter buildFilterSecurityInterceptor(
            @SpringSecurityServices final AccessDecisionManager accessDecisionManager,
            @SpringSecurityServices final AuthenticationManager manager,
            final Collection<RequestInvocationDefinition> contributions ) throws Exception {

        FilterSecurityInterceptor interceptor = new FilterSecurityInterceptor();
        LinkedHashMap<RequestMatcher, Collection<ConfigAttribute>> requestMap = convertCollectionToLinkedHashMap( contributions );
        DefaultFilterInvocationSecurityMetadataSource source =
                new DefaultFilterInvocationSecurityMetadataSource(requestMap);
        interceptor.setAccessDecisionManager( accessDecisionManager );
        interceptor.setAlwaysReauthenticate( false );
        interceptor.setAuthenticationManager( manager );
        interceptor.setSecurityMetadataSource(source);
        interceptor.setValidateConfigAttributes( true );
        interceptor.afterPropertiesSet();
        return new HttpServletRequestFilterWrapper( interceptor );
    }

    static LinkedHashMap<RequestMatcher, Collection<ConfigAttribute>> convertCollectionToLinkedHashMap(
            Collection<RequestInvocationDefinition> urls ) {

        LinkedHashMap<RequestMatcher, Collection<ConfigAttribute>> requestMap = new LinkedHashMap<RequestMatcher, Collection<ConfigAttribute>>();
        for ( RequestInvocationDefinition url : urls ) {
            requestMap.put( url.getRequestMatcher(), url.getConfigAttributeDefinition() );
        }
        return requestMap;
    }

    @Marker( SpringSecurityServices.class )
    public static HttpServletRequestFilter buildHttpSessionContextIntegrationFilter() throws Exception {

      SecurityContextPersistenceFilter filter = new SecurityContextPersistenceFilter();
        filter.setForceEagerSessionCreation( false );
        filter.afterPropertiesSet();
        return new HttpServletRequestFilterWrapper( filter );
    }

    @Marker( SpringSecurityServices.class )
    public static UsernamePasswordAuthenticationFilter buildRealAuthenticationProcessingFilter(
            @SpringSecurityServices final AuthenticationManager manager,
            @SpringSecurityServices final RememberMeServices rememberMeServices,
            @Inject @Value( "${spring-security.check.url}" ) final String authUrl,
            @Inject @Value( "${spring-security.target.url}" ) final String targetUrl,
            @Inject @Value( "${spring-security.failure.url}" ) final String failureUrl,
            @Inject @Value( "${spring-security.always.use.target.url}" ) final String alwaysUseTargetUrl ) throws Exception {

        UsernamePasswordAuthenticationFilter filter = new UsernamePasswordAuthenticationFilter();
        filter.setAuthenticationManager( manager );

        filter.setPostOnly(false);

        filter.setAuthenticationFailureHandler( new SimpleUrlAuthenticationFailureHandler(failureUrl) );

        SavedRequestAwareAuthenticationSuccessHandler successHandler = new SavedRequestAwareAuthenticationSuccessHandler();
        successHandler.setDefaultTargetUrl(targetUrl);
        successHandler.setAlwaysUseDefaultTargetUrl( Boolean.parseBoolean( alwaysUseTargetUrl ) );
        filter.setAuthenticationSuccessHandler( successHandler);
    filter.setRequiresAuthenticationRequestMatcher(new RequestMatcher() {
     
          // copied from AbstractAuthenticationProcessingFilter
      @Override
      public boolean matches(HttpServletRequest request) {
        String uri = request.getRequestURI();
              int pathParamIndex = uri.indexOf(';');

              if (pathParamIndex > 0) {
                  // strip everything after the first semi-colon
                  uri = uri.substring(0, pathParamIndex);
              }

              if ("".equals(request.getContextPath())) {
                  return uri.endsWith(authUrl);
              }

              return uri.endsWith(request.getContextPath() + authUrl);
      }
    });
        filter.setRememberMeServices( rememberMeServices );           

        filter.afterPropertiesSet();
        return filter;
    }

    @Marker( SpringSecurityServices.class )
    public static HttpServletRequestFilter buildAuthenticationProcessingFilter(
            final UsernamePasswordAuthenticationFilter filter ) throws Exception {

        return new HttpServletRequestFilterWrapper( filter );
    }

    @Marker( SpringSecurityServices.class )
    public static HttpServletRequestFilter buildRememberMeProcessingFilter(
            @SpringSecurityServices final RememberMeServices rememberMe,
            @SpringSecurityServices final AuthenticationManager authManager ) throws Exception {

        final RememberMeAuthenticationFilter filter = new RememberMeAuthenticationFilter(authManager,rememberMe);
        filter.afterPropertiesSet();
        return new HttpServletRequestFilterWrapper( filter );
    }

    @Marker( SpringSecurityServices.class )
    public static HttpServletRequestFilter buildSecurityContextHolderAwareRequestFilter() {
      SecurityContextHolderAwareRequestFilter scharf = new SecurityContextHolderAwareRequestFilter();
      try {
      scharf.afterPropertiesSet();
    } catch (ServletException e) {
      throw new TapestryException("Could not initialize SecurityContextHolderAwareRequestFilter",e);
    }
        return new HttpServletRequestFilterWrapper(scharf);
    }

    @Marker( SpringSecurityServices.class )
    public static HttpServletRequestFilter buildAnonymousProcessingFilter(
            @Inject @Value( "${spring-security.anonymous.attribute}" ) final String anonymousAttr,
            @Inject @Value( "${spring-security.anonymous.key}" ) final String anonymousKey ) throws Exception {

       
        final UserAttributeEditor attrEditor = new UserAttributeEditor();
        attrEditor.setAsText( anonymousAttr );
        final UserAttribute attr = (UserAttribute) attrEditor.getValue();
       
        final AnonymousAuthenticationFilter filter = new AnonymousAuthenticationFilter(anonymousKey,"anonymousUser",attr.getAuthorities());
        filter.afterPropertiesSet();
        return new HttpServletRequestFilterWrapper( filter );
    }

    @Marker( SpringSecurityServices.class )
    public static RememberMeServices build(
            final UserDetailsService userDetailsService,
            @Inject @Value( "${spring-security.rememberme.key}" ) final String rememberMeKey ) {

        final TokenBasedRememberMeServices rememberMe = new TokenBasedRememberMeServices(rememberMeKey,userDetailsService);
        return rememberMe;
    }

    @Marker( SpringSecurityServices.class )
    public static LogoutHandler buildRememberMeLogoutHandler(
            final UserDetailsService userDetailsService,
            @Inject @Value( "${spring-security.rememberme.key}" ) final String rememberMeKey ) throws Exception {

        final TokenBasedRememberMeServices rememberMe = new TokenBasedRememberMeServices(rememberMeKey,userDetailsService);
        rememberMe.afterPropertiesSet();
        return rememberMe;
    }

    public static void contributeLogoutService(
            final OrderedConfiguration<LogoutHandler> cfg,
            @Inject RequestGlobals globals,
            @InjectService( "RememberMeLogoutHandler" ) final LogoutHandler rememberMeLogoutHandler ) {

        cfg.add( "securityContextLogoutHandler", new SecurityContextLogoutHandler() );
        cfg.add( "rememberMeLogoutHandler", rememberMeLogoutHandler );
        cfg.add( "tapestryLogoutHandler", new TapestryLogoutHandler( globals ) ,new String[0]);
    }

    @Marker( SpringSecurityServices.class )
    public static AuthenticationManager buildAuthenticationManager( final List<AuthenticationProvider> providers )
            throws Exception {

        final ProviderManager manager = new ProviderManager(providers);
        manager.afterPropertiesSet();
        return manager;
    }

    @Marker( SpringSecurityServices.class )
    public final AuthenticationProvider buildAnonymousAuthenticationProvider(
            @Inject @Value( "${spring-security.anonymous.key}" ) final String anonymousKey ) throws Exception {

        final AnonymousAuthenticationProvider provider = new AnonymousAuthenticationProvider(anonymousKey);
        provider.afterPropertiesSet();
        return provider;
    }

    @Marker( SpringSecurityServices.class )
    public final AuthenticationProvider buildRememberMeAuthenticationProvider(
            @Inject @Value( "${spring-security.rememberme.key}" ) final String rememberMeKey ) throws Exception {

        final RememberMeAuthenticationProvider provider = new RememberMeAuthenticationProvider(rememberMeKey);
        provider.afterPropertiesSet();
        return provider;
    }

    @Marker( SpringSecurityServices.class )
    public final AuthenticationProvider buildDaoAuthenticationProvider(
            final UserDetailsService userDetailsService,
            final PasswordEncoder passwordEncoder,
            final SaltSourceService saltSource ) throws Exception {

        final DaoAuthenticationProvider provider = new DaoAuthenticationProvider();
        provider.setUserDetailsService( userDetailsService );
        provider.setPasswordEncoder( passwordEncoder );
        provider.setSaltSource( saltSource );
        provider.afterPropertiesSet();
        return provider;
    }

    public final void contributeAuthenticationManager(
            final OrderedConfiguration<AuthenticationProvider> configuration,
            @InjectService( "AnonymousAuthenticationProvider" ) final AuthenticationProvider anonymousAuthenticationProvider,
            @InjectService( "RememberMeAuthenticationProvider" ) final AuthenticationProvider rememberMeAuthenticationProvider ) {

        configuration.add( "anonymousAuthenticationProvider", anonymousAuthenticationProvider );
        configuration.add( "rememberMeAuthenticationProvider", rememberMeAuthenticationProvider );
    }

    @Marker( SpringSecurityServices.class )
    public final AccessDecisionManager buildAccessDecisionManager( final List<AccessDecisionVoter> voters )
            throws Exception {
        final AffirmativeBased manager = new AffirmativeBased(voters);
        manager.afterPropertiesSet();
        return manager;
    }

    public final void contributeAccessDecisionManager( final OrderedConfiguration<AccessDecisionVoter> configuration ) {
        configuration.add( "RoleVoter", new RoleVoter() );
    }

    @Marker( SpringSecurityServices.class )
    public static SecurityChecker buildSecurityChecker(
            @SpringSecurityServices final AccessDecisionManager accessDecisionManager,
            @SpringSecurityServices final AuthenticationManager authenticationManager ) throws Exception {

        final StaticSecurityChecker checker = new StaticSecurityChecker();
        checker.setAccessDecisionManager( accessDecisionManager );
        checker.setAuthenticationManager( authenticationManager );
        checker.afterPropertiesSet();
        return checker;
    }

    @Marker( SpringSecurityServices.class )
    public static AuthenticationEntryPoint buildAuthenticationEntryPoint(
            @Inject @Value( "${spring-security.loginform.url}" ) final String loginFormUrl,
            @Inject @Value( "${spring-security.force.ssl.login}" ) final String forceHttps ) throws Exception {

      final LoginUrlAuthenticationEntryPoint entryPoint = new LoginUrlAuthenticationEntryPoint(loginFormUrl);
        entryPoint.afterPropertiesSet();
        boolean forceSSL = Boolean.parseBoolean( forceHttps );
        entryPoint.setForceHttps( forceSSL );
        return entryPoint;
    }

    public static SpringSecurityExceptionTranslationFilter buildSpringSecurityExceptionFilter(
            final AuthenticationEntryPoint aep,
            @Inject @Value( "${spring-security.accessDenied.url}" ) final String accessDeniedUrl ) throws Exception {

        SpringSecurityExceptionTranslationFilter filter = new SpringSecurityExceptionTranslationFilter();
        filter.setAuthenticationEntryPoint( aep );
        if ( !accessDeniedUrl.equals( "" ) ) {
            T5AccessDeniedHandler accessDeniedHandler = new T5AccessDeniedHandler();
            accessDeniedHandler.setErrorPage( accessDeniedUrl );
            filter.setAccessDeniedHandler( accessDeniedHandler );
        }
        filter.afterPropertiesSet();
        return filter;
    }

    public static void contributeRequestHandler(
            final OrderedConfiguration<RequestFilter> configuration,
            final RequestGlobals globals,
            @InjectService( "SpringSecurityExceptionFilter" ) final SpringSecurityExceptionTranslationFilter springSecurityExceptionFilter ) {

        configuration.add( "SpringSecurityExceptionFilter", new RequestFilterWrapper(
                globals,
                springSecurityExceptionFilter ), "after:ErrorFilter" );
    }

    // Contribute three aspects of module: presentation, entities and
    // configuration
    public static void contributeComponentClassResolver( final Configuration<LibraryMapping> configuration ) {

        configuration.add( new LibraryMapping( "security", "nu.localhost.tapestry5.springsecurity" ) );
    }

}
TOP

Related Classes of nu.localhost.tapestry5.springsecurity.services.SecurityModule

TOP
Copyright © 2018 www.massapi.com. All rights reserved.
All source code are property of their respective owners. Java is a trademark of Sun Microsystems, Inc and owned by ORACLE Inc. Contact coftware#gmail.com.