混合多种视图技术:ContentNegotiatingViewResolver

1. 混合多种视图技术

1.1. 目的

同一资源,多种表述,允许你用同样的内容数据来呈现不同的view

1.2. 三种方式

方式1  使用扩展名

http://www.test.com/user.xml    呈现xml文件

http://www.test.com/user.json    呈现json格式

http://www.test.com/user       使用默认view呈现,比如jsp

---------------------------------------------------------------------

方式2  使用http request headerAccept

GET /user HTTP/1.1

Accept:application/xml

GET /user HTTP/1.1

Accept:application/json

---------------------------------------------------------------------

方式3  使用参数

http://www.test.com/user?format=xml

http://www.test.com/user?format=json

1.3. ContentNegotiatingViewResolver配置文件说明

ContentNegotiatingViewResolver该解析器是Spring 3.0新增的,它不负责具体的视图解析,而是作为一个中间人的角色根据请求所要求的MIME类型,从上下文中选择一个适合的视图解析器,再将视图解析工作委托其负责

<bean class="org.springframework.web.servlet.view.BeanNameViewResolver" 
p:order="0" >
</bean>
<!-- 混合多种视图技术 -->
<bean class="org.springframework.web.servlet.view.ContentNegotiatingViewResolver"
p:order="1"
p:defaultContentType="text/html"
p:ignoreAcceptHeader="true"
p:favorPathExtension="false"
p:favorParameter="true"
p:parameterName="content"
>
<property name="mediaTypes">
<map>
<entry key="html" value="text/html"></entry>
<entry key="xml" value="application/xml"></entry>
<entry key="json" value="application/json"></entry>
</map>
</property>
<property name="defaultViews">
<list>
  <bean	     
           class="org.springframework.web.servlet.view.json.MappingJacksonJsonView" 
       p:renderedAttributes="jsonData">
          </bean>
          <bean class="org.springframework.web.servlet.view.xml.MarshallingView" 
               p:modelKey="xmlData" p:marshaller-ref="xmlMarshaller"></bean> 
</list>
</property>
</bean>
<bean id="xmlMarshaller"
    class="org.springframework.oxm.xstream.XStreamMarshaller">
<property name="streamDriver">
<bean class="com.thoughtworks.xstream.io.xml.StaxDriver"></bean>
</property>
<property name="autodetectAnnotations" ><value>true</value></property>
<property name="annotatedClasses">
<list>
<value>com.loushi135.model.User</value>
</list>
</property>
</bean>
<bean class="org.springframework.web.servlet.view.<span style="font-family: 宋体;">InternalResourceViewResolver</span>" 
p:order="100" >  
<property name="viewClass" 
                value="org.springframework.web.servlet.view.JstlView" />  
    <property name="prefix" value="/WEB-INF/jsp/"/>  
<property name="suffix" value=".jsp"/>
</bean> 
<bean id="userListExcelView" class="com.loushi135.view.UserListExcelView"></bean>
<bean id="userListPoiExcelView" 
   class="com.loushi135.view.UserListPoiExcelView"></bean>
<bean id="userListPdfView" class="com.loushi135.view.UserListPdfView"></bean>
说明:

1.BeanNameViewResolver

视图解析器,根据视图的名称new ModelAndView(name),在配置文件查找对应的bean配置,返回视图'userListExcelView'就进入userListExcelView处理

2. defaultContentType

如果所有的mediaType扩展名都没匹配上,就会使用defaultContentType

3.ignoreAcceptHeader

是否忽略掉accept header,默认就是false

4. favorPathExtension

是否启用扩展名支持,默认就是true

5.favorParameter

是否启用参数支持,默认就是true

6.parameterName

参数支持的参数名,默认为format

7.mediaTypes

扩展名至mediaType的映射关系

8.renderedAttributes="jsonData"

json对象根属性

9.xmlMarshaller

也可以使用Jaxb2Marshaller

<span style="color:#333333;"><bean class="org.springframework.web.servlet.view.xml.MarshallingView">
    <constructor-arg>
        <bean class="org.springframework.oxm.jaxb.Jaxb2Marshaller">
            <property name="classesToBeBound">
                <array>     
			<value>com.hoo.entity.User</value>          
			<value>com.hoo.entity.AccountBean</value>             
			<value>com.hoo.entity.MapBean</value>
                </array>
            </property>
        </bean>
    </constructor-arg>
</bean></span>
10. streamDriver

设置驱动,StaxDriver,DomDriver

1.3.1. UserController 

package com.loushi135.controller;
import java.util.ArrayList;
import java.util.List;
import org.springframework.stereotype.Controller;
import org.springframework.ui.ModelMap;
import org.springframework.web.bind.annotation.RequestMapping;
import com.loushi135.model.User;
@Controller
@RequestMapping("/user")
public class UserController {
private List<User> userList = new ArrayList<User>();
public UserController() {
super();
for(int i = 0;i<5;i++){
User user = new User();
user.setName("loushi"+i);
user.setPassword("password"+i);
userList.add(user);
}
}
@RequestMapping("/userIndex")
public String toUserIndex(){
return "userIndex";
}
/**
 * 返回json数据
 */
@RequestMapping("/getJson")
public String getJson(ModelMap mm){
mm.addAttribute("jsonData", userList);
return "listJson";
}
/**
 * 返回xml数据
 */
@RequestMapping("/getXml")
public String getXml(ModelMap mm){
mm.addAttribute("xmlData", userList);
return "listXml";
}
/**
 * 返回excel数据
 */
@RequestMapping("/getExcel")
public String getExcel(ModelMap mm){
mm.addAttribute("userList",userList);
return "userListExcelView";
}
/**
 * 返回excel数据
 */
@RequestMapping("/getPoiExcel")
public String getPoiExcel(ModelMap mm){
mm.addAttribute("userList",userList);
return "userListPoiExcelView";
}
/**
 * 返回pdf数据
 */
@RequestMapping("/getPdf")
public String getPdf(ModelMap mm){
mm.addAttribute("userList",userList);
return "userListPdfView";
}
}

1.3.2. jxl返回Excel视图

package com.loushi135.view;
import java.util.List;
import java.util.Map;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import jxl.WorkbookSettings;
import jxl.format.Alignment;
import jxl.format.VerticalAlignment;
import jxl.write.WritableCellFormat;
import jxl.write.WritableFont;
import jxl.write.WritableSheet;
import jxl.write.WritableWorkbook;
import jxl.write.WriteException;
import jxl.write.biff.RowsExceededException;
import org.apache.commons.beanutils.PropertyUtils;
import org.springframework.web.servlet.view.document.AbstractJExcelView;
import com.loushi135.model.User;
public class UserListExcelView extends AbstractJExcelView {
private String[] columnNames = new String[] {"姓名","密码"};  
private String[] dbColumnNames = new String[] {"name","password"};  
private Integer[] columnWidths = new Integer[] { 40, 40 }; 
@Override
protected void buildExcelDocument(Map<String, Object> model,
WritableWorkbook workbook, HttpServletRequest request,
HttpServletResponse response) throws Exception {
try { 
response.setCharacterEncoding("UTF-8");
response.setContentType("application/ms-excel");
String fileName = "用户列表excel.xls";
//	 response.setContentType("APPLICATION/OCTET-STREAM");  
  response.setHeader("Content-Disposition", "inline; filename="+new String(fileName.getBytes(),"iso8859-1"));  
        String sheetName = "用户信息";
        // 全局设置  
        WorkbookSettings setting = new WorkbookSettings();  
        java.util.Locale locale = new java.util.Locale("zh", "CN");  
        setting.setLocale(locale);  
        setting.setEncoding("UTF-8");  
        // 创建工作薄  
//	        workbook = Workbook.createWorkbook(os); // 建立excel文件  
        // 创建第一个工作表  
        jxl.write.WritableSheet ws = workbook.createSheet(sheetName, 1); // sheet名称  
List<User> userList = (List<User>)model.get("userList");
 // 添加标题  
        addColumNameToWsheet(ws);
        writeContext(ws, userList);  
} catch (Exception e) {  
        e.printStackTrace();  
    } 
//	 finally {  
        // 写入文件  
//	        try {  
//	        	workbook.write();  
//	        	workbook.close();  
//	            os.flush();  
//	            os.close();  
//	        } catch (WriteException e) {  
//	            e.printStackTrace();  
//	        } catch (IOException e) {  
//	            e.printStackTrace();  
//	        }  
//	    }  
}  
    private <T> void writeContext(WritableSheet wsheet, List<T> list) {  
        jxl.write.Label wlabel = null;  
        jxl.write.WritableCellFormat wcf = getFormat();  
        int rows = list.size();  
        int cols = dbColumnNames.length;  
        String columnName = null;  
        Object value = null;  
        try {  
            for (int i = 0; i < rows; i++) {  
                T t = (T) list.get(i);                
                for (int j = 0; j < cols; j++) {  
                    columnName = dbColumnNames[j].toLowerCase();  
                    value = PropertyUtils.getProperty(t, columnName);  
                    wlabel = new jxl.write.Label(j, (i + 1), value + "", wcf);  
                    wlabel = new jxl.write.Label(j, (i + 1), value + "");  
                    wsheet.addCell(wlabel);  
                }
            }  
        } catch (Exception e) {  
            e.printStackTrace();  
        }  
  
    }  
    // 添加标题样式  
    private void addColumNameToWsheet(jxl.write.WritableSheet wsheet)  
            throws RowsExceededException, WriteException {  
  
        // 设置excel标题  
        jxl.write.WritableFont wfont = getFont();  
        if (null == wfont) {  
            wfont = new WritableFont(WritableFont.ARIAL,  
                    WritableFont.DEFAULT_POINT_SIZE, WritableFont.BOLD);  
  
        }  
        jxl.write.WritableCellFormat wcfFC = getFormat();  
        if (null == wcfFC) {  
            wcfFC = new jxl.write.WritableCellFormat(wfont);  
            try {  
                wcfFC.setWrap(true);// 自动换行  
                wcfFC.setAlignment(Alignment.CENTRE);  
                wcfFC.setVerticalAlignment(VerticalAlignment.CENTRE);// 设置对齐方式  
            } catch (WriteException e) {  
                e.printStackTrace();  
            }  
        }  
        jxl.write.Label wlabel1 = null;  
        String[] columNames = columnNames;  
        if (null == columNames)  
            return;  
        int colSize = columNames.length;  
  
        Integer[] colsWidth = columnWidths;  
        if (null == colsWidth) {  
            colsWidth = new Integer[colSize];  
            for (int i = 0; i < colSize; i++) {  
                colsWidth[i] = 20;  
            }  
        }  
        int temp = 0;  
        String colName = null;  
        for (int i = 0; i < colSize; i++) {  
            colName = columNames[i];  
            if (null == colName || "".equals(colName))  
                colName = "";  
            wlabel1 = new jxl.write.Label(i, 0, colName, wcfFC);  
            wsheet.addCell(wlabel1);  
            temp = colsWidth[i].intValue();  
            // 默认设置列宽  
            temp = temp == 0 ? 20 : temp;  
            wsheet.setColumnView(i, temp);  
        }  
    }  
    // 设置格式  
    private WritableCellFormat getFormat() {  
        jxl.write.WritableFont wfont = getFont();  
        jxl.write.WritableCellFormat wcfFC = new jxl.write.WritableCellFormat(  
                wfont);  
        try {  
            wcfFC.setWrap(true);  
            wcfFC.setAlignment(Alignment.CENTRE);  
            wcfFC.setVerticalAlignment(VerticalAlignment.CENTRE);  
        } catch (WriteException e) {  
            e.printStackTrace();  
        }  
        return wcfFC;  
    }  
    // 设置字体  
    private WritableFont getFont() {  
        return new WritableFont(WritableFont.ARIAL,  
                WritableFont.DEFAULT_POINT_SIZE, WritableFont.BOLD);  
    }  
}

1.3.3. poi返回excel

package com.loushi135.view;
import java.util.List;
import java.util.Map;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import org.apache.poi.hssf.usermodel.HSSFCellStyle;
import org.apache.poi.hssf.usermodel.HSSFRow;
import org.apache.poi.hssf.usermodel.HSSFSheet;
import org.apache.poi.hssf.usermodel.HSSFWorkbook;
import org.springframework.web.servlet.view.document.AbstractExcelView;
import com.loushi135.model.User;
public class UserListPoiExcelView extends AbstractExcelView {
@Override
protected void buildExcelDocument(Map<String, Object> model,
HSSFWorkbook workbook, HttpServletRequest request,
HttpServletResponse response) throws Exception {
String fileName = "用户列表excel.xls";
        // 设置response方式,使执行此controller时候自动出现下载页面,而非直接使用excel打开  
        response.setContentType("APPLICATION/OCTET-STREAM");  
        response.setHeader("Content-Disposition", "inline; filename="+new String(fileName.getBytes(),"iso8859-1"));  
        List<User> userList = (List<User>) model.get("userList");     
        // 产生Excel表头  
        HSSFSheet sheet = workbook.createSheet("用户列表");  
        HSSFRow header = sheet.createRow(0); // 第0行  
        // 产生标题列  
        header.createCell((short) 0).setCellValue("name");  
        header.createCell((short) 1).setCellValue("password");  
        HSSFCellStyle cellStyle = workbook.createCellStyle();  
  
        // 填充数据  
        int rowNum = 1;  
        for (User user:userList) {  
            HSSFRow row = sheet.createRow(rowNum++);  
            row.createCell((short) 0)  
                    .setCellValue(user.getName().toString());  
            row.createCell((short) 1).setCellValue(user.getPassword());  
        }  
  
//        // 列总和计算  
//        HSSFRow row = sheet.createRow(rowNum);  
//        row.createCell((short) 0).setCellValue("TOTAL:");  
//        String formual = "SUM(D2:D" + rowNum + ")"; // D2到D[rowNum]单元格起(count数据)  
//        row.createCell((short) 3).setCellFormula(formual);  
}
}

1.3.4. 返回pdf视图

package com.loushi135.view;
import java.awt.Color;
import java.util.List;
import java.util.Map;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import org.springframework.web.servlet.view.document.AbstractPdfView;
import com.loushi135.model.User;
import com.lowagie.text.Document;
import com.lowagie.text.Paragraph;
import com.lowagie.text.pdf.BaseFont;
import com.lowagie.text.pdf.PdfPCell;
import com.lowagie.text.pdf.PdfPTable;
import com.lowagie.text.pdf.PdfWriter;
public class UserListPdfView extends AbstractPdfView {
@Override
protected void buildPdfDocument(Map<String, Object> model,
Document document, PdfWriter writer, HttpServletRequest request,
HttpServletResponse response) throws Exception {
String fileName = "用户列表pdf.pdf";
        // 设置response方式,使执行此controller时候自动出现下载页面,而非直接使用excel打开  
        response.setContentType("APPLICATION/OCTET-STREAM");  
        response.setHeader("Content-Disposition", "inline; filename="+new String(fileName.getBytes(),"iso8859-1"));    
        List<User> userList = (List<User>) model.get("userList");            
        //显示中文  
        BaseFont bfChinese = BaseFont.createFont("STSong-Light", "UniGB-UCS2-H", BaseFont.NOT_EMBEDDED);   
        com.lowagie.text.Font FontChinese = new com.lowagie.text.Font(bfChinese, 12, com.lowagie.text.Font.NORMAL );          
        //创建一个有2列的表格
        PdfPTable table = new PdfPTable(2);
        //定义一个表格单元
        PdfPCell cell = new PdfPCell(new Paragraph("header with colspan 2"));
        //定义一个表格单元的跨度
        cell.setColspan(2);
        //定义单元格的背景颜色
        cell.setBackgroundColor(new Color(0xC0, 0xC0, 0xC0));
        table.addCell(cell);
        PdfPCell headName = new PdfPCell(new Paragraph("姓名",FontChinese));
        //定义单元格的框颜色
        headName.setBorderColor(new Color(255, 0, 0));
        PdfPCell headPassword = new PdfPCell(new Paragraph("密码",FontChinese));
        headPassword.setBorderColor(new Color(255, 0, 0));
        table.addCell(headName);
        table.addCell(headPassword);
        for (User user:userList) {   
        	 PdfPCell name = new PdfPCell(new Paragraph(user.getName(),FontChinese));
        	 PdfPCell password = new PdfPCell(new Paragraph(user.getPassword(),FontChinese));
        	 table.addCell(name);
        	 table.addCell(password);
        }  
        document.add(table);
}
}

1.3.5. 测试jsp页面

<%@ page language="java" import="java.util.*" pageEncoding="utf-8"%>
<%
String path = request.getContextPath();
String basePath = request.getScheme()+"://"+request.getServerName()+":"+request.getServerPort()+path+"/";
%>
<!DOCTYPE HTML PUBLIC "-//W3C//DTD HTML 4.01 Transitional//EN">
<html>
  <head>
    <meta http-equiv="Content-Type" content="text/html; charset=ISO-8859-1" />
    <title>视图</title>
<script type="text/javascript"
src="${pageContext.request.contextPath}/js/jquery-1.8.1.js"></script>
<script type="text/javascript">
    	var _ctx="${pageContext.request.contextPath}";
  	$(document).ready(function(){
  	   $("#json").click(function(event){
  	       $.post(
  	    	    _ctx+"/user/getJson.do?content=json",//请求使用content=?来实现restful风格,来选择进入什么视图
  	    	    {},
  	    	    function(data){
  	    	    var jsonData = data.jsonData;
  	    	    var message = "";
  	    	    $(jsonData).each(function(i,item){//解析json
  	    	  message +=" 用户名:"+item.name+"  密码:"+item.password;
  	    	   });
  	    	    alert(message);
  	    	    },
  	    	    'json'
  	    	    );
  	   });
  	   
  	 $("#xml").click(function(event){
  	       $.post(
  	    	    _ctx+"/user/getXml.do?content=xml",
  	    	    {},
  	    	    function(data){
  	    	  var message = "";
  	    	 $(data).find("User").each(function(i,item){//解析xml
  	    	 var name = $(item).children('name').text();
  	    	 var password = $(item).children('password').text();
  	    	 message +=" 用户名:"+name+"  密码:"+password;
  	    	    });
  	    	 alert(message);
  	    	    },
  	    	    'xml'
  	    	    );
  	   });
  	 
  	 });
  	</script>
  </head>
  <body>
     <input type="button" value="请求返回json" id="json"/>
     <br/>
     <input type="button" value="请求返回xml" id="xml"/>
     <br>
     <input type="button" value="请求jxl返回excel" id="jxlExcel" οnclick="location='${pageContext.request.contextPath}/user/getExcel.do'"/>
     <br/>
     <input type="button" value="请求poi返回excel" id="poiExcel" οnclick="location='${pageContext.request.contextPath}/user/getPoiExcel.do'"/>
     <br/>
     <input type="button" value="请求返回pdf" id="pdf" οnclick="location='${pageContext.request.contextPath}/user/getPdf.do'"/>
     <br/>
     <input type="button" value="请求返回模板" id="template"/>
  </body>
</html>


通过http://localhost:8080/SpringMvcHelloWorld/user/userIndex.do 进入 userIndex.jsp



 

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值