之前我很热衷于写一些采集程序,这都得感谢2009我在游戏蜗牛软件的一上司,因为他我才整整的开始接触网络编程。那时候SNS开始流行,蜗牛网也是一个SNS,所以肯定缺少不了一个邮箱好友邀请的程序,我从一个没有接触过URL类的初级程序员,开始研究,花了半年时间,终于凑合的写出了一个支持网易163、126、yeah, sohu,sina,hotmail,tom,yahoo等主流邮箱的好友读取程序。
后来因为老婆怀孕了,我就离开了苏州,来到了昆山,因为昆山遍地台资,工资少,但是当地的Java人员十分饱和,我于是只好进了一家台资的MIS部门混日子。
在这个期间,我的工作就是维护产线上的java程序不出问题,所以相当的闲,每天除了研究我有兴趣的程序,就是面壁打瞌睡(那时候我的面前是一堵墙)。
在MIS的时候,我开始接触到了各种php框架,wordpress,phpwind,dedecms,discuz!等等,这些都是主流的中小型网站的框架程序。
我的博客http://www.ij2ee.com 采用的是wordpress程序,有一天我看到了一种xmlrpc协议,使用这种协议我就可以发布程序
详情参考:http://www.ij2ee.com/48971.html
具体使用xmlrpc发送文章代码 需要apache的xmlrpc包支持:
package com.feed.common; import java.net.MalformedURLException; import java.net.URL; import java.util.HashMap; import java.util.Map; import org.apache.xmlrpc.XmlRpcException; import org.apache.xmlrpc.client.XmlRpcClient; import org.apache.xmlrpc.client.XmlRpcClientConfigImpl; import com.feed.vo.Article; /** * 提交文章类 * * @author jeson.sha * @blog http://www.ij2ee.com/ */ public class CommonPostAction { XmlRpcClientConfigImpl config = null; XmlRpcClient client = null; public CommonPostAction(String xmlrpc) { if (config == null) { config = new XmlRpcClientConfigImpl(); try { config.setServerURL(new URL(xmlrpc)); } catch (MalformedURLException e) { // TODO Auto-generated catch block e.printStackTrace(); } if (client == null) client = new XmlRpcClient(); client.setConfig(config); } // TODO Auto-generated constructor stub } private static CommonPostAction action; public static CommonPostAction getInstance(String xmlrpc) { if (action == null) { action = new CommonPostAction(xmlrpc); } return action; } @SuppressWarnings("unchecked") public String postArticle(Article a) { Map post = new HashMap(); post.put("title", a.getTitle());// 标题 post.put("mt_keywords", a.getKeyword()); // CnBlogsParser.tag);// 标签 Object[] categories = new Object[] { a.getKeyword() }; post.put("categories", categories); post.put("description", a.getBody());// 内容 Object[] params = new Object[] { a.isDisPost() ? "1" : "0", a.getUser(), a.getPwd(), post, true }; // 1代表正式发布,0代表草稿 String ob; try { ob = (String) client.execute("metaWeblog.newPost", params); } catch (XmlRpcException e) { // TODO Auto-generated catch block e.printStackTrace(); try { Thread.sleep(7000L); } catch (InterruptedException e1) { // TODO Auto-generated catch block e1.printStackTrace(); } return ""; } System.out.println("Created with blogid " + ob); return ""; } @SuppressWarnings("unchecked") public String postArticle(Article a, String keyword, Object[] categories, String user, String pwd) { Map post = new HashMap(); post.put("title", a.getTitle());// 标题 post.put("mt_keywords", a.getKeyword()); // CnBlogsParser.tag);// 标签 post.put("categories", new Object[] { a.getKeyword() }); post.put("description", a.getBody());// 内容 Object[] params = new Object[] { a.isDisPost() ? "1" : "0", user, pwd, post, true }; // 1代表正式发布,0代表草稿 String ob; try { ob = (String) client.execute("metaWeblog.newPost", params); } catch (XmlRpcException e) { e.printStackTrace(); try { Thread.sleep(7000L); } catch (InterruptedException e1) { e1.printStackTrace(); } return ""; } System.out.println("Created with blogid " + ob); return ""; } }
因为有了在蜗牛的网页抓取、分析、解析基础,我就可以从任意一个布局规范的网站抓取任意我所需要的内容到我的博客。
你必须要有以下基础才能玩的得心应手:
- HTTP头的认知
- 正则表达式
- HTMLParser类
- 网页分析能力
如果需要高级点的玩法,比如要登录才能获取内容,或者要回帖才能看到内容,那就需要会使用apache的httpclient类。
httpclient可以参照这篇文章:http://www.ij2ee.com/47694.html
因为我是抓取cnblogs文章的,日子久后我发现这样分析不见得是件好事,太耗资源(当然,任何电脑都耗得起这个资源)。
我找到了更好的取代方法,那就是直接读取 RSS 需要rome包的支持.
这个包的下载地址:http://mirrors.ibiblio.org/pub/mirrors/maven2/rome/rome/0.9/rome-0.9.jar
rss说白了就是一种日志的xml描述。我们只需要学会解析xml就行了。
下面是我的一段feed的解析
private void parser() throws Exception { SyndFeedInput input = new SyndFeedInput(); InputStream ins = new URL(feedUrl).openStream(); SyndFeed feed = input.build(new XmlReader(ins, encoding)); List<SyndEntry> entries = feed.getEntries(); for(SyndEntry en : entries){ try { if(getToday==1){ Date postDate = en.getUpdatedDate(); if(postDate==null||postDate.toString().length()<5){ List modList = en.getModules(); if(modList!=null&&!modList.isEmpty()){ Module m = (Module) modList.get(0); if(m instanceof DCModuleImpl){ DCModuleImpl dcm = (DCModuleImpl) m; postDate = dcm.getDate(); } } } boolean isToday = isToday(postDate); if(isToday==false){ continue; //break; } } onePostParse(en); } catch (Exception e) { // TODO Auto-generated catch block e.printStackTrace(); } } }
综合上面的解析feed和发送代码,我们就可以灵活的去写这个程序。
出于网络垃圾的减少(当然我也是垃圾制造者),我并不打算公布整个项目。上面是核心代码段。希望大家能好好利用。