Category Archives: Tomcat

Add CORS management with Tomcat and Angular-Js

In one of my projects, I decided to setup a SOA architecture using Angular-Js as the UI layer. My main focus is to have a clear separation between the business and the presentation. Another benefit of this is that it is possible the use different servers to these 2 parts.
But doing this causes an issue, because of security, an Ajax request cannot connect to a server which is in another domain from where it is originated. It is done like that to avoid some malicious code executed in a page sends information to another server but in my case, it’s a problem. This behavior is called the Cross-origin Resource Sharing and fortunately, most modern browsers (it excludes IE) can deal with this but the server needs more configuration.
On the server side (Tomcat), there is a provided filter that we need to add to our web configuration (CorsFilter).
In the web.xml, we add:

<filter>
    <filter-name>CorsFilter</filter-name>
    <filter-class>org.apache.catalina.filters.CorsFilter</filter-class>
    <init-param>
        <param-name>cors.allowed.origins</param-name>
        <param-value>*</param-value>
    </init-param>
    <init-param>
        <param-name>cors.allowed.methods</param-name>
        <param-value>GET,POST,HEAD,OPTIONS,PUT,DELETE</param-value>
    </init-param>
</filter>

I added also some parameters but the default values should be enough.

Now, the server can manage the headers sent by the browser and with this configuration, the filter will automatically allow the request, it is also possible to configure the filter to restrict access to certain domains, but in my case, as I am already in a restricted network, it is not needed.

Another issue I encountered was with the web session. My services need an authenticated user, it is done using an authentication page and a web session. But when the CORS principle is used, by default, the browser does not send the session cookie, to enable it, I added in my Angular app:

var classNotFound = angular.module('classNotFound', ['ngRoute', 'ui.bootstrap', ...])
	.config(['$httpProvider', function($httpProvider) {//mandatory to enable cors feature (http://en.wikipedia.org/wiki/Cross-origin_resource_sharing)
		$httpProvider.defaults.withCredentials = true;
	}])

Now it works!

Define configuration file outside of the classpath

Here I describe the way I use to configure my applications. The main idea is to define a property file outside of the application, doing this, it is possible to deploy the same application in several environments (dev/test/prod) without any changes.

First of all, the property file:

net.classnotfound.app.jdbc.server=db-server
net.classnotfound.app.jdbc.port=1521
net.classnotfound.app.jdbc.sid=xe
net.classnotfound.app.jdbc.user=scott
net.classnotfound.app.jdbc.password=koala

The tips is to define a parameter in the Tomcat context file which points to the file location:

<Parameter name="directoryConfig" override="false" value="FILE_PATH"/>

And now, to get the value in the application, I use Spring this way:

<bean id="placeholderConfig"
	class="org.springframework.beans.factory.config.PropertyPlaceholderConfigurer">
	<property name="location"
		value="file:#{contextParameters.directoryConfig}/app-config.properties" />
</bean>

This is an example of its usage to set up an Oracle datasource:

<orcl:pooling-datasource id="dataSource"
	url="jdbc:oracle:thin:@${net.classnotfound.app.jdbc.server}:${net.classnotfound.app.jdbc.port}:${net.classnotfound.app.jdbc.sid}"
	username="${net.classnotfound.app.jdbc.user}" password="${net.classnotfound.app.jdbc.password}">
</orcl:pooling-datasource>

Now, we can just change the path of the configuration file, depending on each environment, to automatically have the related parameters.

Starting of Spring context in web application

Using Spring in a web application, we need to load the context when the application starts. Fortunately, it can be done in a simple way, by adding the right listener in the application web.xml.

Using Maven, you need to add the Spring-web dependency in your pom.xml:

<dependency>
  <groupId>org.springframework</groupId>
  <artifactId>spring-web</artifactId>
  <version>4.0.0.RELEASE</version>
  <scope>compile</scope>
</dependency>

And in the web.xml:

<listener>
    <listener-class>org.springframework.web.context.ContextLoaderListener</listener-class>
</listener>

Tomcat Datasource configuration

I describe here my favorite solution to define the datasource of my web applications.

To do that in Tomcat :

  1. Copy the JDBC driver jar into the Tomcat lib directory
  2. define the datasource in the file server.xml:
     <GlobalNamingResources>
    
        <Resource 
            auth="Container" 
            driverClassName="oracle.jdbc.OracleDriver" 
            maxActive="20" 
            maxIdle="10" 
            maxWait="-1" 
            name="jdbc/myGlobalDatasource" 
            password="password" 
            type="javax.sql.DataSource" 
            url="jdbc:oracle:thin:@[server]:[port]:[sid]" 
            username="user"/>
    
    </GlobalNamingResources>
  3. map this datasource to your application using its context.xml file:
    <ResourceLink 
        global="jdbc/globalDatasource" 
        name="jdbc/applicationDatasource" 
        type="javax.sql.DataSource"/>
  4. And now, when you want to use it (using Spring):
    <bean id="dataSource" class="org.springframework.jndi.JndiObjectFactoryBean">
        <property name="jndiName" value="jdbc/applicationDatasource" />
        <property name="resourceRef" value="true" />
    </bean>

Done!

This example uses an Oracle connection but it can be easily adapted for another database.