Interview Questions

Spring - Abstract View

Consider a scenario, where you want to display content of an xml file or provide an excel/pdf as a part of http response in a spring based web application. Spring framework, provides an abstract view for this purpose.

AbstractView is an abstract class in spring api, provided with methods which should be implemented by the subclass, so that it can be sent as View inside the ModelAndView object from a spring controller.

This class is a simple replacement for jsp. Instead of redirecting the output to a jsp, we are using a concrete class extending the AbstractView class.

Have a look at the following class DataView.java

DataViewController .java

import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import org.springframework.web.servlet.mvc.multiaction.MultiActionController;

public class DataViewController extends MultiActionController
{
        public ModelAndView dataViewHandler(HttpServletRequest request, HttpServletResponse response) throws Exception
        {
                ModelAndView mv = null;
                try
                {
                        Map<String, Object> model = new HashMap<String, Object>();

                        DataView view = new DataView();
                        mv = new ModelAndView(view, model);
                }
                catch (Exception e)
                {

                }
                return mv;
        }
}

The above class overrides renderMergedOutputModel() method from AbstractView. This method should contain code to write to the response.

You also need to set the contentType of the response using the setContentType() method in the AbstractView class. Have a look at the following Controller class which uses the DataView class.

DataView.java

import java.io.BufferedReader;
import java.io.File;
import java.io.FileInputStream;
import java.io.FileReader;
import java.util.Map;

import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;

import org.apache.commons.logging.LogFactory;
import org.springframework.web.servlet.view.AbstractView;

public class DataView extends AbstractView
{

        protected static final String   CONTENT_TYPE    = "application/xml; charset=UTF-8";

        public DataView()
        {
                setContentType(CONTENT_TYPE);
        }

        /*
         * (non-Javadoc)
         * @see org.springframework.web.servlet.view.AbstractView#renderMergedOutputModel(java.util.Map,
         * javax.servlet.http.HttpServletRequest, javax.servlet.http.HttpServletResponse)
         */

        @Override
        protected void renderMergedOutputModel(Map arg0, HttpServletRequest request, HttpServletResponse response)
                        throws Exception
        {
                try
                {
                        response.setContentType("application/xml; charset=UTF-8");
                        String locReport = "C:\\techdive.xml";

                        response.setContentType(getContentType());

                        response.getWriter().write(getFileContentAsString(new BufferedReader(new FileReader(locReport))));
                }
                catch (Exception e)
                {
                }
        }

        public byte[] getFileContentAsBytes(File file) throws Exception
        {
                FileInputStream fileInputStream = new FileInputStream(file);
                byte[] byteArray = new byte[1024];
                byte[] result = new byte[0];
                int start = 0;
                int end = byteArray.length;
                int count = 0;
                while ((count = fileInputStream.read(byteArray, start, end - 1)) != -1)
                {
                        byte[] temp = new byte[result.length + count];
                        System.arraycopy(byteArray, 0, temp, result.length, count);
                        result = temp;
                }
                return result;
        }

        public String getFileContentAsString(BufferedReader bufferedReader) throws Exception
        {
                BufferedReader buf = new BufferedReader(bufferedReader);

                StringBuffer sBuf = new StringBuffer();
                String s = null;

                while ((s = buf.readLine()) != null)
                {
                        sBuf.append(s);
                }
                return sBuf.toString();
        }
}

Here is the spring config xml file for the above context.

<bean id="dataViewController" class="in.techdive.DataViewController ">
               
<property name="methodNameResolver">
<bean id=" dataViewControllerMethodNameResolver" class="org.springframework.web.servlet.mvc.multiaction.PropertiesMethodNameResolver">
               
        <property name="mappings">
                <prop key="/getDataView.htm">getDataViewHandler</prop>
        </property>
        </bean>
</property>
</bean>

In this way, we can use Abstract View for rendering the view in spring based web applications.