Spring security: allow a few pages to be displayed in iframe - spring-mvc

I support a website that uses Spring Security (5.3.3.RELEASE). The site can't be displayed in iframe in other sites because of the following configuration
<security:headers>
<security:frame-options policy="SAMEORIGIN"/>
</security:headers>
Now I am asked to allow a few pages to be displayed in iframe in ANY other sites (not a specific list of sites). I looked at the Spring documentation, and it appears that I can add a bean in the following way:
<security:headers>
<security:frame-options policy="SAMEORIGIN" ref="bean_id"/>
</security:headers>
I am not able to find info about what interface or methods the bean (bean_id) must implement or whether it can be used to decide what pages are frameable. Any help or example is really appreciated.

The interface is of type AllowFromStrategy. But that interface is deprecated since the ALLOW-FROM is an obsolete directive that no longer works in modern browsers, see here. The alternative is to use CSP: frame-ancestors.
Spring Security has support for the Content-Security-Policy header. You can rely on the DelegatingRequestMatcherHeaderWriter implementation to add the headers only to specific pages, like so:
<http>
<!-- ... -->
<headers>
<header ref="headerWriter"/>
</headers>
</http>
<beans:bean id="headerWriter"
class="org.springframework.security.web.header.writers.DelegatingRequestMatcherHeaderWriter">
<beans:constructor-arg>
<bean class="org.springframework.security.web.util.matcher.AntPathRequestMatcher"
c:pattern="/page-with-csp"/>
</beans:constructor-arg>
<beans:constructor-arg>
<beans:bean
class="org.springframework.security.web.header.writers.ContentSecurityPolicyHeaderWriter"/>
</beans:constructor-arg>
</beans:bean>

Related

Spring Security Oauth2 XML Configuration in Detail

I want to use the xml configuration file for registering clients for OAUTH2 in my web application. I know that there exist support for xml tags using the client-registrations tag
However I want to register the client registration repository as a bean. So that it is extensible, something like this:
<beans:bean id="clientRegistrationRepository" class="org.springframework.security.oauth2.client.registration.ClientRegistrationRepository">
<beans:constructor-arg index="0" ref="clientRegistration"/>
</beans:bean>
... more tags expanding clientRegistration
However this does not work. Does any one know how we can do this ?

Spring MVC: how to make site language selection remembered across browsers?

I am using Spring MVC for a website with two languages: English and Chinese.
I have the following in the Spring context
<bean id="localeChangeInterceptor" class="org.springframework.web.servlet.i18n.LocaleChangeInterceptor">
<property name="paramName" value="lang" />
</bean>
I am able to see the language of the website changes if I select another language through a dropdown in the HTML interface.
Suppose I am viewing the website when its language is Chinese. I close the browser. Then I open the browser again and I enter the url of the website without the lang parameter in the URL.
Here is the issue: Chrome is able to remember what the language was when the browser was closed and use that language when the new browser window is opened. This is the behavior I want to have. However, Firefox does not. When I open it and enter the site url, it always shows the site in the site's default language (English in this case).
How can I make the Firefox (or other browsers) open the site with the language used when it was closed?
Thanks!
You also need to add a SessionLocaleResolver.
<bean id="localeResolver" class="org.springframework.web.servlet.i18n.SessionLocaleResolver">
<property name="defaultLocale" value="en" />
</bean>
If you do not add this then I'm pretty sure the default behavior is that the AcceptHeaderLocaleResolver will be used, which resolves the locale by checking the accept-language header in the HTTP request. This means your browser will make the determination, use your language preferences and send the language choice in the accept header.
If your application is stateless then you may need to use the CookieLocaleResolver instead.
After research, I found out the solution. I need to set locale resolver this way:
<bean id="localeResolver"
class="org.springframework.web.servlet.i18n.CookieLocaleResolver">
<property name="defaultLocale" value="en" />
<property name="cookieName" value="clientLang" />
<property name="cookieMaxAge" value="31556926" />
</bean>
Put it another, I need to give it life to persistent for some time by setting a value to cookieMaxAge. I tested it out in Firefox and Safari, it worked well. This thread has the credit:
When I used CookieLocaleResolver, I can set invalid cookie to crash spring web application
Cheers!

Which are the classes used for User Authentication in alfresco.4.2.c in the case of External SSO?

I am trying to implement External SSO in alfresco share. I am using alfresco.4.2.c.
I want to enable debug mode for the classes which are using for Authentication in the case of External SSO.
So please let me know the class names which are using in External SSO.
Depends on which SSO you are integrating say OpenAM, CAS etc
SlingshotUserFactory class is used for default authentication in Alfresco Share
You can override its entry as below in share-config-custom.xml
<config evaluator="string-compare" condition="WebFramework">
<web-framework>
<!-- SpringSurf Autowire Runtime Settings -->
<!-- Developers can set mode to 'development' to disable; SpringSurf caches,
FreeMarker template caching and Rhino JavaScript compilation. -->
<defaults>
<page-type>
<id>login</id>
<page-instance-id>slingshot-login</page-instance-id>
</page-type>
<user-factory>webframework.factory.user.custom.slingshot
</user-factory>
</defaults>
</web-framework>
</config>
Add below entry in custom-slingshot-application-context.xml
<bean id="webframework.factory.user.custom.slingshot" class="com.test.web.site.ExtSlingshotUserFactory"
parent="webframework.factory.user.slingshot">
</bean>
now on login it will call your class for authentication

make .html default view spring mvc

Have a sample app and created a
view/HelloWorld.html
page. From my controller, I return the following
public String home(Locale locale, Model model) {
return "HelloWorld";
}
In debug mode I get this warning/error:
WARN : org.springframework.web.servlet.PageNotFound - No mapping found for HTTP request with URI [/HelloWorld/WEB-INF/views/HelloWorld.html] in DispatcherServlet with name 'appServlet'
contents of my src/main/webapp/WEB-INF/spring/appServlet/servlet-context.xml
<!-- DispatcherServlet Context: defines this servlet's request-processing infrastructure -->
<!-- Enables the Spring MVC #Controller programming model -->
<annotation-driven />
<!-- Handles HTTP GET requests for /resources/** by efficiently serving up static resources in the ${webappRoot}/resources directory -->
<resources mapping="/resources/**" location="/resources/" />
<!-- Resolves views selected for rendering by #Controllers to .jsp resources in the /WEB-INF/views directory -->
<beans:bean class="org.springframework.web.servlet.view.InternalResourceViewResolver">
<beans:property name="prefix" value="/WEB-INF/views/" />
<beans:property name="suffix" value=".html" />
</beans:bean>
If I rename the .html to .jsp and change above to .jsp then things work fine.
The flow that the servlet container goes through for this request is the following:
First the DispatcherServlet is invoked by the Servlet Container.
The DispatcherServlet finds a mapping which maps to the home method of your Controller and the home method returns a view name "HelloWorld"
Now the DispatcherServlet uses a View Resolver (your InternalResourceViewResolver) to find the View to render the model through, since the name is "HelloWorld", this maps to the /WEB-INF/view/HelloWorld.html view.
Now essentially a call is made to RequestDispatcher.forward("/WEB-INF/views/HelloWorld.html",....
The Servlet container at this point tries to find the servlet which can handle /WEB-INF/views/HellowWorld.html uri - if it had been a .jsp there is a JSPServlet registered which can handle rendering the jsp, however for *.html there is no servlet registered, so the call ends up with the "default servlet", which is registered with a servlet-mapping of / which probably your DispatcherServlet is.
Now the Dispatcher servlet does not find a controller to handle request for /WEB-INF/views/HelloWorld.html and hence the message that you are seeing
If you want this kind of a extension to be handled by the servlet container, say tomcat, you can register *.html extension to be handled by JSPServlet and then it should work cleanly. Or return forward:/resources/HelloWorld.html which will be considered a static file relative to your resources folder.
There's a lot of difference between html and jsp. Java server pages are compiled into Java ‘servlets’. It may call beans and enterprise beans, such as Java Beans components and Enterprise Java Beans components, to execute processing on the server. So, having such JSP technology could be a key component in high-level architecture for web-based applications.

Spring MVC : using wildcards in <mvc:resources>

I'm implementing a cache busting system for a Spring MVC application.
For this system to work, I have to strip the "cache busting code" from a given url. Let's say my generated cache busting code is "123" and I have a .css url that is: /public-123/css/style.css. In this example, I want /public/css/style.css to be succesfully called (-123 must be stripped).
This works in my "mvc-config.xml" context file:
<mvc:resources mapping="/public-123/**" location="/public/" />
But I would also like any cache busting code to work, even if it's not the current one. For example, I would also like /public-456/css/style.css to reach the style.css file.
If I try to add another wildcard to the mapping:
<mvc:resources mapping="/public-*/**" location="/public/" />
It doesn't work! I receive a 404....
How could I specify the "mapping" attribute so any code after the "public-" part is well managed?
One way to handle this is to use Spring EL, as shown in the Spring docs:
<mvc:resources mapping="/resources-#{applicationProps['application.version']}/**" location="/public-resources/"/>
You could probably store the "123" part in a properties file so it only gets set once. E.g. via property-placeholder:
<context:property-placeholder location="classpath:myApp.properties"/>
<mvc:resources mapping="/resources-${cache.code}/**" location="/public-resources/"/>
This has the advantage of being able to read this code in your JSP pages (to generate links) via the same properties value.
I managed to get this working by manually defining the ResourceHttpRequestHandler to handle assets that are located on the filesystem alongside the <mvc:resources /> tag:
<bean id="assetsResourceHandler" class="org.springframework.web.servlet.resource.ResourceHttpRequestHandler">
<property name="locations">
<list>
<bean class="org.springframework.core.io.UrlResource">
<constructor-arg value="file:#{applicationProps['assets.basedir']}"></constructor-arg>
</bean>
</list>
</property>
</bean>
I guess you're doing this to achieve cache busting for your static resources.
In the meantime, Spring 4.1 has dedicated features for this, so you can remove a lot of that custom configuration.
Something like this:
<mvc:resources mapping="/public/**" location="/public/"/>
<mvc:resource-chain resource-cache="true">
<mvc:resolvers>
<mvc:version-resolver>
<mvc:content-version-strategy patterns="/**"/>
</mvc:version-resolver>
</mvc:resolvers>
</mvc:resource-chain>
</mvc:resources>

Resources