文档章节

实现类似OSChina博客的导出功能

Harmel
 Harmel
发布于 2015/08/14 18:05
字数 479
阅读 151
收藏 5

实现原理:从数据库中查询出所有的文章信息,将文章信息转成XML文档,再通过XSLT文档对其转换成HTML文档后进行下载。

1、将文章信息转成XML文档

private static Document articlesToXML(List<Article> articles, String title) {
    Document doc = DocumentHelper.createDocument();
    Element root = doc.addElement("articles").addAttribute("title", title);
    for (Article article : articles) {
        Element articleEle = root.addElement("article");
        articleEle.addElement("title").setText(article.getTitle());
        articleEle.addElement("content").setText(article.getContent());
    }
    return doc;
}

转换后的XML类似于如下

<?xml version="1.0" encoding="UTF-8"?>
<articles title="我的博客">
    <article>
        <title>文章标题</title>
        <content>文章内容</content>
    </article>
</articles>

2、将XML文档转成HTML

public static byte[] articlesToHTML(List<Article> articles, String title) {
    ByteArrayOutputStream out = new ByteArrayOutputStream();
    try {
        TransformerFactory factory = TransformerFactory.newInstance();
        InputStream in = ArticleUtils.class.getClassLoader().getResourceAsStream("article.xsl");
        Source xlst = new StreamSource(in);
        Transformer transformer = factory.newTransformer(xlst);
        Source xmlSource = new DocumentSource(articlesToXML(articles, title));
        Result outputTarget = new StreamResult(out);
        transformer.transform(xmlSource, outputTarget);
        in.close();
    } catch (Exception e) {
        throw new RuntimeException("文章集合转HTML数据失败", e);
    }
    return out.toByteArray();
}

XSLT文档

<?xml version="1.0" encoding="UTF-8"?>
<xsl:stylesheet version="1.0"
    xmlns:xsl="http://www.w3.org/1999/XSL/Transform">
    <xsl:template match="/">
        <html>
            <head>
                <meta http-equiv="Content-Type" content="text/html;charset=UTF-8" />
                <title>
                    <xsl:value-of select="/articles[@title]/@title" />
                </title>
                <style type="text/css">
                    body{
                        background-color: #F5F5F5;
                        color: #797979;
                    }

                    h2{
                        color: #2B9B70;
                        margin: 15px;
                    }
                    
                    .article{
                        margin: 15px;
                        background-color: white;
                    }

                    .article_title {
                        color: #2B9B70;
                        font-size: 20px;
                        border-bottom: 1px dashed #2B9B70;
                        padding: 10px;
                    }

                    .article_content {
                        padding: 8px 15px;
                        line-height: 1.8;
                    }
                </style>
            </head>
            <body>
                <h2><xsl:value-of select="/articles[@title]/@title" /></h2>
                <xsl:apply-templates />
            </body>
        </html>
    </xsl:template>
    <xsl:template match="article">
        <div class="article">
            <div class="article_title">
                <xsl:value-of select="title" disable-output-escaping="yes" />
            </div>
            <div class="article_content">
                <xsl:value-of select="content" disable-output-escaping="yes" />
            </div>
        </div>
    </xsl:template>
</xsl:stylesheet>

3、实现下载 -- Struts2

public class ExportAction extends BaseAction {

    @Resource(name = "articleService")
    private ArticleService articleService;

    // 文件名
    public String getFileName() throws IOException {
        String blogTitle = (String) application.get("blog_title");
        String fileName = blogTitle + "-" + DateUtils.getDate(new Date(), "yyyyMMddHHmmss") + ".html";
        // 解决火狐和IE文件名编码差异
        HttpServletRequest request = ServletActionContext.getRequest();
        String agent = request.getHeader("user-agent");
        if (agent.contains("Firefox")) {
            fileName = "=?UTF-8?B?" + new BASE64Encoder().encode(fileName.getBytes("UTF-8")) + "?=";
        } else {
            fileName = URLEncoder.encode(fileName, "UTF-8");
        }
        return fileName;
    }

    // 下载流
    public InputStream getTargetFile() {
        String blogTitle = (String) application.get("blog_title");
        byte[] bytes = ArticleUtils.articlesToHTML(articleService.findAllArticles(), blogTitle);
        return new ByteArrayInputStream(bytes);
    }

}

Struts2配置文件

<action name="export" class="exportAction">
    <result type="stream">
        <param name="inputName">targetFile</param>
        <param name="contentType">text/html</param>
        <param name="contentDisposition">attachment;filename=${fileName}</param>
    </result>
</action>

© 著作权归作者所有

共有 人打赏支持
Harmel
粉丝 9
博文 33
码字总数 14582
作品 0
武汉
程序员
私信 提问
wordpress博客批量导入OSchina博客

wordpress博客批量导入OSchina博客 Wordpress有同步文章到百度hi空间、新浪博客等的插件,没有同步到OSchina博客的插件,而OSChina也没有提供博客导入的功能。就简单用代码(java)实现了这功能...

youthflies
2013/09/28
0
4
osc动弹里的@功能和#功能 实现方案

各位,我想做一个博客方面的功能,比如我在文章里有 oschina 的关键字,会自动链接到我的站点下的oschina百科里,这样的功能如何实现?类似osc动弹里的@功能和#功能。 谢谢!...

lateron
2012/12/04
249
2
oschina导出博客获取图片

oschina通过“博客导出”功能可以导出不带图片的html文档,img标签中的src全部指向oschina,如何获取这些博客中的图片: 1、解析出导出博客的图片地址,下载图片,为图片命名并修改src属性值...

樂天
2013/01/25
0
0
OSChina 博客导出功能

很多人不放心将博客放在 OSChina 上,担心某天可能会访问不到。 这个担心是非常可以理解的,为了打消这个担心,我们也相应有几条应对措施: 1. OSChina会一直开下去,OSChina的服务器成本可通...

红薯
2010/04/08
552
7
OSCHINA 博客新增导出所有文章的功能

继年前刚推出的使用 Live Writer 写博客的功能后。 OSCHINA 的博客新增导出所有文章的功能,进入个人空间管理 -> 博客管理 -> 博客导出,便会弹出下载对话框,备份的文件是 html 格式,可以直...

红薯
2012/01/25
3.3K
34

没有更多内容

加载失败,请刷新页面

加载更多

分布式项目(五)iot-pgsql

书接上回,在Mapping server中,我们已经把数据都整理好了,现在利用postgresql存储历史数据。 iot-pgsql 构建iot-pgsql模块,这里我们写数据库为了性能考虑不在使用mybatis,换成spring jd...

lelinked
今天
2
0
一文分析java基础面试题中易出错考点

前言 这篇文章主要针对的是笔试题中出现的通过查看代码执行结果选择正确答案题材。 正式进入题目内容: 1、(单选题)下面代码的输出结果是什么? public class Base { private Strin...

一看就喷亏的小猿
今天
1
0
cocoapods 用法

cocoapods install pod install 更新本地已经install的仓库 更新所有的仓库 pod update --verbose --no-repo-update 更新制定的仓库 pod update ** --verbose --no-repo-update...

HOrange
今天
3
0
linux下socket编程实现一个服务器连接多个客户端

使用socekt通信一般步骤 1)服务器端:socker()建立套接字,绑定(bind)并监听(listen),用accept()等待客户端连接。 2)客户端:socker()建立套接字,连接(connect)服务器,连接上后...

shzwork
昨天
3
0
android自定义viewgroup画背景

设计部要求背景实现一个背景边框带圆弧的效果: 所以想着用自定义控件画一个背景。 为了方便,继承的是LinearLayout,在onMeasure中先获取控件宽高: @Overrideprotected void onMeasure(in...

醉雨
昨天
1
0

没有更多内容

加载失败,请刷新页面

加载更多

返回顶部
顶部