johnnyGor
johnnyGor

Reputation: 161

Magnolia CMS with Blossom + spring security

I have question to magnolia blossom users regarding spring security I'm trying to follow all guidelines provided on magnolia cms pages but no one of them works for me. I have configured web.xml and spring security context in the way it was described + my own configuration for retrieving user from db. I can start application with jetty(eclipse) without any any errors about beans etx, but I can't achieve situation when login page appears. When running in on my developer magnolia jetty instance I'm asked to login using magnolia page, after successfully login there is no spring security forcing me to log one more time. This is the example url

http://localhost:9999/magnolia-blossom-sample-webapp/home/tours/statues-tour.html

When deploying to public magnolia instance on tomcat I'm not asked to login into magnolia but I get my pages without login page with spring security.

http://localhost:8080/magnoliaPublic/home/tours.html

The question is what I could missed there that I can't get authorisation page to login with spring security.

This is my configuration

Magnolia public/author web.xml ( since web.xml is not placed in my blossom module)

  <filter>
    <display-name>Magnolia global filters</display-name>
    <filter-name>magnoliaFilterChain</filter-name>
    <filter-class>info.magnolia.cms.filters.MgnlMainFilter</filter-class>
  </filter>
  <filter-mapping>
    <filter-name>magnoliaFilterChain</filter-name>
    <url-pattern>/*</url-pattern>
    <dispatcher>REQUEST</dispatcher>
    <dispatcher>FORWARD</dispatcher>
    <dispatcher>INCLUDE</dispatcher>
    <dispatcher>ERROR</dispatcher>
  </filter-mapping>
    <filter>
  <filter-name>springSecurityFilterChain</filter-name>
  <filter-class>info.magnolia.module.blossom.web.InstallationAwareDelegatingFilterProxy</filter-class>
</filter>
<filter-mapping>
  <filter-name>springSecurityFilterChain</filter-name>
  <url-pattern>/home/*</url-pattern> // /* doesn't work neither
</filter-mapping>
  <listener>
    <listener-class>info.magnolia.init.MagnoliaServletContextListener</listener-class>
  </listener>
  <context-param>
    <description>Vaadin production mode</description>
    <param-name>productionMode</param-name>
    <param-value>true</param-value>
  </context-param>

Spring security context applicationContext-security.xml

<?xml version="1.0" encoding="UTF-8"?>
<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/security 
    http://www.springframework.org/schema/security/spring-security-3.1.xsd
        http://www.springframework.org/schema/beans http://www.springframework.org/schema/beans/spring-beans.xsd"
        default-autowire="byType">

    <beans:bean id="authSuccessHandler" class="security.auth.AuthenticationSuccessHandler">
        <beans:property name="userLogic" ref="userLogic"/>
    </beans:bean>

    <beans:bean id="authFailureHandler" class="security.auth.AuthenticationFailureHandler">
    </beans:bean>

    <http auto-config="true" use-expressions="true">
        <intercept-url pattern="/**" access="isAuthenticated()" />
        <intercept-url pattern="/*" access="hasRole('adminMLM')" />
        <form-login login-page="/login"         
            authentication-success-handler-ref="authSuccessHandler"
            authentication-failure-handler-ref="authFailureHandler"
            default-target-url="/"      
        />
        <logout />
    </http>

    <beans:bean id="daoAuthenticationProvider" class="org.springframework.security.authentication.dao.DaoAuthenticationProvider">
      <beans:property name="userDetailsService" ref="userLogic"/>     
      <beans:property name="passwordEncoder" ref="userLogic"/>
      <beans:property name="saltSource" ref="userLogic"/>
    </beans:bean>

    <authentication-manager>
      <authentication-provider ref="daoAuthenticationProvider" />
    </authentication-manager>




</beans:beans>

applicationContext.xml

<?xml version="1.0" encoding="UTF-8"?>
<beans xmlns="http://www.springframework.org/schema/beans"
       xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xmlns:blossom="http://www.magnolia-cms.com/schema/blossom"
       xsi:schemaLocation="http://www.springframework.org/schema/beans 
       http://www.springframework.org/schema/beans/spring-beans.xsd 
       http://www.magnolia-cms.com/schema/blossom 
       http://www.magnolia-cms.com/schema/blossom.xsd ">

  <bean class="info.magnolia.blossom.sample.module.service.SalesApplicationWebServiceImpl" />

  <bean id="springSecurityFilterChain" class="org.springframework.web.filter.DelegatingFilterProxy"/>



</beans>

blossom-servlet.xml

<?xml version="1.0" encoding="UTF-8"?>
<beans xmlns="http://www.springframework.org/schema/beans"
       xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
       xmlns:context="http://www.springframework.org/schema/context"
       xsi:schemaLocation="http://www.springframework.org/schema/beans http://www.springframework.org/schema/beans/spring-beans.xsd http://www.springframework.org/schema/context http://www.springframework.org/schema/context/spring-context.xsd">

  <context:annotation-config/>

  <context:component-scan base-package="logic.impl" />
  <context:component-scan base-package="info.magnolia.blossom.sample.module" use-default-filters="false">
    <context:include-filter type="annotation" expression="info.magnolia.module.blossom.annotation.Template"/>
    <context:include-filter type="annotation" expression="info.magnolia.module.blossom.annotation.Area"/>
    <context:include-filter type="annotation" expression="info.magnolia.module.blossom.annotation.DialogFactory"/>
    <context:include-filter type="annotation" expression="info.magnolia.module.blossom.annotation.VirtualURIMapper"/>
    <context:include-filter type="assignable" expression="info.magnolia.cms.beans.config.VirtualURIMapping"/>
  </context:component-scan>


  <bean class="org.springframework.web.servlet.mvc.method.annotation.RequestMappingHandlerAdapter">
    <property name="customArgumentResolvers">
      <list>
        <bean class="info.magnolia.module.blossom.web.BlossomHandlerMethodArgumentResolver" />
      </list>
    </property>
    <!-- For @Valid - JSR-303 Bean Validation API -->
    <property name="webBindingInitializer">
      <bean class="org.springframework.web.bind.support.ConfigurableWebBindingInitializer">
        <property name="validator">
          <bean class="org.springframework.validation.beanvalidation.LocalValidatorFactoryBean" />
        </property>
      </bean>
    </property>
  </bean>

  <bean class="info.magnolia.module.blossom.preexecution.BlossomHandlerMapping">
    <property name="targetHandlerMappings">
      <list>
        <bean class="org.springframework.web.servlet.mvc.method.annotation.RequestMappingHandlerMapping">
          <property name="useSuffixPatternMatch" value="false" />
        </bean>
        <bean class="org.springframework.web.servlet.handler.BeanNameUrlHandlerMapping" />
      </list>
    </property>
  </bean>

  <bean class="org.springframework.web.servlet.mvc.SimpleControllerHandlerAdapter" />

  <bean class="info.magnolia.module.blossom.view.UuidRedirectViewResolver">
    <property name="order" value="1" />
  </bean>

  <!-- JSP - renders all views that end with .jsp -->
  <bean class="info.magnolia.module.blossom.view.TemplateViewResolver">
    <property name="order" value="2"/>
    <property name="prefix" value="/templates/blossomSampleModule/"/>
    <property name="viewNames" value="*.jsp"/>
    <property name="viewRenderer">
      <bean class="info.magnolia.module.blossom.view.JspTemplateViewRenderer">
        <property name="contextAttributes">
          <map>
            <entry key="damfn">
              <bean class="info.magnolia.rendering.renderer.ContextAttributeConfiguration">
                <property name="name" value="damfn"/>
                <property name="componentClass" value="info.magnolia.dam.asset.functions.DamTemplatingFunctions"/>
              </bean>
            </entry>
          </map>
        </property>
      </bean>
    </property>
  </bean>

  <!-- Freemarker - renders all views that end with .ftl -->
  <bean class="info.magnolia.module.blossom.view.TemplateViewResolver">
    <property name="order" value="3"/>
    <property name="prefix" value="/blossomSampleModule/"/>
    <property name="viewNames" value="*.ftl"/>
    <property name="viewRenderer">
      <bean class="info.magnolia.module.blossom.view.FreemarkerTemplateViewRenderer">
        <property name="contextAttributes">
          <map>
            <entry key="cms">
              <bean class="info.magnolia.rendering.renderer.ContextAttributeConfiguration">
                <property name="name" value="cms"/>
                <property name="componentClass" value="info.magnolia.templating.freemarker.Directives"/>
              </bean>
            </entry>
            <entry key="cmsfn">
              <bean class="info.magnolia.rendering.renderer.ContextAttributeConfiguration">
                <property name="name" value="cmsfn"/>
                <property name="componentClass" value="info.magnolia.templating.functions.TemplatingFunctions"/>
              </bean>
            </entry>
            <entry key="damfn">
              <bean class="info.magnolia.rendering.renderer.ContextAttributeConfiguration">
                <property name="name" value="damfn"/>
                <property name="componentClass" value="info.magnolia.dam.asset.functions.DamTemplatingFunctions"/>
              </bean>
            </entry>
          </map>
        </property>
      </bean>
    </property>
  </bean>




</beans>

BlossomSampleModule.java

public class BlossomSampleModule extends BlossomModuleSupport implements ModuleLifecycle {

    public void start(ModuleLifecycleContext moduleLifecycleContext) {
        if (moduleLifecycleContext.getPhase() == ModuleLifecycleContext.PHASE_SYSTEM_STARTUP) {
            super.initRootWebApplicationContext("classpath:/applicationContext.xml");
            super.initBlossomDispatcherServlet("blossom", "classpath:/blossom-servlet.xml, classpath:/applicationContext-security.xml");

        }
    }

    public void stop(ModuleLifecycleContext moduleLifecycleContext) {
        if (moduleLifecycleContext.getPhase() == ModuleLifecycleContext.PHASE_SYSTEM_SHUTDOWN) {
            super.destroyDispatcherServlets();
            super.closeRootWebApplicationContext();
        }
    }
}

Best Regards

Upvotes: 0

Views: 1309

Answers (1)

Jan
Jan

Reputation: 4369

Last filter in Magnolia's filter chain - RenderingFilter behaves as terminator in filter chain. If it finds content to render from Magnolia (or via Blossom), it will not continue to process filter chain, hence your other filter (spring security) will not be executed. You need to make sure that either your filter is executed before Magnolia filter chain or inside of Magnolia filter chain. To achieve the later, please define your filter within Magnolia's AdminCentral under config:/server/filters ... any place there after ContextFilter and before CacheFilter should be fine. Use other filters there as examples on how to configure yours or look at here or here.

HTH,

Jan

Upvotes: 2

Related Questions