Spring FAQ

Spring @Service Vs @Controller
http://stackoverflow.com/questions/15922991/is-spring-annotation-controller-same-as-service
————————-
Spring @Controller Vs @restcontroller
https://www.genuitec.com/spring-frameworkrestcontroller-vs-controller/

@RestController = @Controller + @ResponseBody

————————-

Spring Boot with multiple Dispatcher Servlet
http://stackoverflow.com/questions/30670327/spring-boot-with-multiple-dispatcherservlet-each-having-their-own-controllers
————————-

Spring MVC
Dispatcher Servlet

http://www.cubearticle.com/articles/framework/spring/spring-mvc
http://terasolunaorg.github.io/guideline/1.0.1.RELEASE/en/Overview/SpringMVCOverview.html
————————-

Spring quick reference tutorial …outdated in few places…
http://www.javatpoint.com/spring-tutorial

Why we need to copy XSD files to source repo?

Problem Statement: From production Spring application can’t access spring servers for XSD files.
It is better to keep XSD files along with source code for following reasons.
1. Easy to access local system, rather going outside network. (Security issues)
2. Sometimes third party sites are down. During that we can’t do anything.

Solution:
If we have more than 10 files, it is difficult to copy manually those XSD files and prepare mapping files in spring.schemas file. For this reason, I written this code.
Input: Search all xml files and find list of XSDs referred in source code. Use text editor and xls to sort them and remove duplicates. Put list of URLs in input_xsd_urls.txt file.
Example:
http://www.springframework.org/schema/batch/spring-batch-2.1.xsd
http://www.springframework.org/schema/beans/spring-beans-3.1.xsd
http://www.springframework.org/schema/cache/spring-cache.xsd
http://www.springframework.org/schema/context/spring-context-3.0.xsd

Output:
This program creates folders in given path and copy files from respective source.
At the end it gives mapping to put in spring.schemas file. Issue solved.

import java.io.BufferedReader;
import java.io.DataInputStream;
import java.io.File;
import java.io.FileInputStream;
import java.io.FileOutputStream;
import java.io.InputStreamReader;
import java.net.MalformedURLException;
import java.net.URL;
import java.nio.channels.Channels;
import java.nio.channels.ReadableByteChannel;
import java.util.ArrayList;
import java.util.List;

/**
 * This is used to download XSD files to respective locations.
 * 
 * @author Bhavani P Polimetla
 * @since 11/29/2012
 * 
 */
public class XSDDownloader {

	/**
	 * @param args
	 */
	public static void main(String[] args) {

		String ROOT = "C:/xsd_download/";
		StringBuffer mappingFile = new StringBuffer();

		// Step 1: Read input file and load it
		List<String> list = getXSDURLsList(ROOT + "input_xsd_urls.txt");

		// Step 2: Create folders in given location
		for (String file : list) {

			try {
				URL aURL = new URL(file);
				System.out.println("path = " + aURL.getPath());
				String[] parts = aURL.getPath().split("/");

				StringBuffer sbPart = new StringBuffer();
				for (int i = 0; i < parts.length - 1; i++) {
					sbPart.append(parts[i]).append("/");
				}
				String targetDir = ROOT + "/META-INF/xsd/" + sbPart.toString();

				System.out.println("folder path==>" + targetDir);

				// Create Directories
				File dir = new File(targetDir);
				dir.mkdirs();

				// Download File
				String targetFile = ROOT + "/META-INF/xsd/" + aURL.getPath();
				downloadFile(file, targetFile);

				// Create Mapping File
				// http://drools.org/schema/drools-service-spring.xsd=drools-service-spring.xsd
				mappingFile.append(file).append("=").append("/META-INF/xsd/")
						.append(aURL.getPath()).append("n");

			} catch (MalformedURLException e) {
				e.printStackTrace();
			}

			// during test, comment this.
			// break;
		} // End of for loop

		System.out.println("Add this to spring.schemas file==>");
		String mappingContent = mappingFile.toString();
		mappingContent = mappingContent.replaceAll("//", "/");
		mappingContent = mappingContent.replaceAll("http:", "http\\:/");
		System.out.println(mappingContent);

	}

	/**
	 * Download file from URL to given file location.
	 * 
	 * @param url
	 * @param destinationFile
	 */
	public static void downloadFile(String url, String destinationFile) {
		try {
			URL website = new URL(url);
			ReadableByteChannel rbc = Channels.newChannel(website.openStream());
			FileOutputStream fos = new FileOutputStream(destinationFile);
			fos.getChannel().transferFrom(rbc, 0, 1 << 24);
			fos.close();
		} catch (Exception ex) {
			ex.printStackTrace();
		}
	}

	/**
	 * The file contains
	 * http://www.springframework.org/schema/batch/spring-batch-2.1.xsd one
	 * entry like this in each file.
	 * 
	 * @param fileName
	 * @return
	 */
	public static List<String> getXSDURLsList(String fileName) {
		List<String> files = new ArrayList<String>();
		try {
			// Open the file that is the first
			// command line parameter
			FileInputStream fstream = new FileInputStream(fileName);
			// Get the object of DataInputStream
			DataInputStream in = new DataInputStream(fstream);
			BufferedReader br = new BufferedReader(new InputStreamReader(in));
			String strLine;
			// Read File Line By Line
			while ((strLine = br.readLine()) != null) {
				// Print the content on the console
				System.out.println(strLine);
				files.add(strLine);
			}
			// Close the input stream
			in.close();
		} catch (Exception e) {// Catch exception if any
			System.err.println("Error: " + e.getMessage());
		}

		return files;
	}

}

References:
http://stackoverflow.com/questions/1729307/spring-schemalocation-fails-when-there-is-no-internet-connection
https://code.google.com/p/spring-crypto-utils/

Scheduling – Spring – Quartz

It is difficult to debate J2SE Vs J2EE scheduling. I.e Java timer utils Vs Quartz Scheduler.
I prefer to use Quartz, because it is most used, proven and well developed product.

http://onjava.com/onjava/2004/03/10/quartz.html

http://www.opensymphony.com/quartz/wikidocs/Tutorial.html
http://static.springsource.org/spring/docs/1.2.9/reference/scheduling.html
http://www.opensymphony.com/quartz/wikidocs/CronTriggers%20Tutorial.html

Finally it runs in Spring Container. If we need to simulate in Unit Tests or Eclipse for testing purpose use following sample code.

Unit Test Code / Example Code to initialize it.
It is not required, If we are running in container.

Spring Configuration File

<bean name="testJob" class="org.springframework.scheduling.quartz.JobDetailBean">
  <property name="jobClass" value="com.abcd.TestJob"/>
  <property name="jobDataAsMap">
    <map>
      <entry key="timeout" value="5"/>
    </map>
  </property>
</bean>

<bean id="cronTrigger" class="org.springframework.scheduling.quartz.CronTriggerBean">
  <property name="jobDetail" ref="testJob"/>
	<!-- run every minute -->
	<!-- Seoncs, Minutes, Hours, day of month, month, day of week, year -->
  <property name="cronExpression" value="0 * * * * ?"/>
</bean>

<bean id="schedulerFactoryBean" class="org.springframework.scheduling.quartz.SchedulerFactoryBean">
  <property name="triggers">
    <list>
      <ref bean="cronTrigger"/>
    </list>
  </property>
  <property name="schedulerContextAsMap">
  	<map>
  	    <!-- The following classes are injected to jobClass by Quartz. Not by spring -->
  	    <entry key="propertyName" value-ref="referenceBeanName"/>
  	</map>
   </property>
</bean>

TestJob.java

package com.abcd;

import java.util.Date;

import org.quartz.JobExecutionContext;
import org.quartz.JobExecutionException;
import org.springframework.scheduling.quartz.QuartzJobBean;

public class TestJob extends QuartzJobBean {

	private int timeout;

	public void setTimeout(int timeout) {
		System.out.println(&quot;setTimeout==&gt;&quot; + timeout);
		this.timeout = timeout;
	}

	@Override
	protected void executeInternal(JobExecutionContext arg0)
			throws JobExecutionException {
		System.out.println(&quot;Job executed&quot; + new Date());

	}

}

TestScheduler.java

package com.asdf;

import java.util.Date;

import org.quartz.impl.StdScheduler;

public class TestScheduler {

	public static &lt;T&gt; T getObjectFromSpringContainer(final String beanId, final Class&lt;T&gt; clazz )
	{
		//Do coding to load Spring configuration files.
		return null;
	}

	public static void main(String[] str){
		
		//This starts the scheduler for testing purpose
		StdScheduler sch = (StdScheduler) getObjectFromSpringContainer(&quot;schedulerFactoryBean&quot;,StdScheduler.class);

		for (int i = 0; i &lt; 999999; i++) {
			System.out.println(&quot;Sleeping and waiting for scheduler to pickup jobs.==&gt;&quot; + i);
			try {
		
				System.out.println(&quot;is Started==&gt;&quot;+sch.isStarted());
				System.out.println(&quot;time pass loop:&quot;+new Date());
				
				Thread.sleep(60000);
			} catch (Exception ex) {
				ex.printStackTrace();
			}
		}
	}
}

http://www.docjar.com/docs/api/org/springframework/scheduling/quartz/QuartzJobBean.html
http://forum.springsource.org/showthread.php?t=76974