eXtremeTable和MyFaces的兼容性问题及解决方法

Displaytag只能通过GET方式提交,所以对于jsf_state_64这样超长的表单就无能为力了。这个时候,我会选择eXtremeTable。extremeTable可以选择是Get方式还是Post方式。但是,ExtremeTable和MyFaces结合作数据导出Excel却出现了问题,无论怎么设置,导出的文件都是乱码。同样的问题也出现在Displaytag中。

我参考了extremeTable和Displaytag的代码,发现他们实现数据导出的方式(就是那个Filter)都是一样的,而ExtremeTable后台采用pio作为Excel导出引擎,我测试了一下,发现后台的导出没有问题。那么问题一定出在那个filter上。extremeTable在结合Struts或Spring mvc的时候都没有问题,那么会不会是extremeTable和myfaces不兼容呢。

我将ExportFilter和AbstractExportFilter拿出来,进行跟踪分析,发现他们对response对象进行了包装(wrapper),而myFaces也对response对象进行了包装,于是,我便重新实现了ExportFilter:

public class ExportFilter extends AbstractExportFilter {
  private static Log log = LogFactory.getLog(ExportFilter.class);
 
  private boolean responseHeadersSetBeforeDoFilter;
 

  public void init(FilterConfig filterConfig) throws ServletException {
    String responseHeadersSetBeforeDoFilter = filterConfig
        .getInitParameter("responseHeadersSetBeforeDoFilter");
    if (StringUtils.isNotBlank(responseHeadersSetBeforeDoFilter)) {
      this.responseHeadersSetBeforeDoFilter = new Boolean(
          responseHeadersSetBeforeDoFilter).booleanValue();
    }
  }

  /**
   * 覆盖(override)<code>AbstractExportFilter</code>的实现
   */
  public void doFilter(ServletRequest request, ServletResponse response,
      FilterChain chain) throws IOException, ServletException {
    Context context = new HttpServletRequestContext(
        (HttpServletRequest) request);
    boolean isExported = ExportFilterUtils.isExported(context);
    if (isExported) {
      String exportFileName = ExportFilterUtils.getExportFileName(context);
      doFilterInternal(request, response, chain, exportFileName);
      //如果ServletResponse是经过包装之后的,那么必须取回原始的那个,否则会引起导出文件错误
      //不过,这个处理会导致一个java.lang.IllegalStateException异常,这不会影响使用
      if(response instanceof ServletResponseWrapper) {
        log.debug("Found wrapped ServletResponse '" + response.getClass().getName() + "'");
        response = ((ServletResponseWrapper) response).getResponse();
      }
      handleExport((HttpServletRequest) request,
          (HttpServletResponse) response, context);
    } else {
      chain.doFilter(request, response);
    }
  }

  protected void doFilterInternal(ServletRequest request,
      ServletResponse response, FilterChain chain, String exportFileName)
      throws IOException, ServletException {
    if (responseHeadersSetBeforeDoFilter) {
      setResponseHeaders((HttpServletResponse) response, exportFileName);
    }
    log.debug(response.getClass().getName());

    chain.doFilter(request, new ExportResponseWrapper(
        (HttpServletResponse) response));
    // chain.doFilter(request, response);
    if (!responseHeadersSetBeforeDoFilter) {
      setResponseHeaders((HttpServletResponse) response, exportFileName);
    }
  }

  public void destroy() {
    // TODO Auto-generated method stub

  }

}

测试了一下,没有问题了。只是会抛出一个异常,但是不会影响使用。

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值