Skip to content

Instantly share code, notes, and snippets.

@cherenkov
Created October 2, 2012 05:38
Show Gist options
  • Star 0 You must be signed in to star a gist
  • Fork 0 You must be signed in to fork a gist
  • Save cherenkov/3816418 to your computer and use it in GitHub Desktop.
Save cherenkov/3816418 to your computer and use it in GitHub Desktop.
Javascript / RSS / Limechat 現在使用しているスクリプトの改造.. - 人力検索はてな http://q.hatena.ne.jp/1349127857
// Javascript / RSS / Limechat 現在使用しているスクリプトの改造.. - 人力検索はてな
// http://q.hatena.ne.jp/1349127857
// gede99 @ http://pen2.com/rss_check/
var version = "rss_check.js v0.06";
// チェックするRSSのURLと発言先
var rss_urls={
"http://feedproxy.google.com/hatena/b/hotentry":"#発言先channelA",
"http://b.hatena.ne.jp/entrylist?sort=hot&threshold=3&mode=rss":"#発言先channelA",
"http://stackoverflow.com/feeds":"#発言先channelA"
};
// 抽出条件 {"url":/RegExp/}
var match = {};
var unmatch = {};
// URL変換
var get_loc = {};
// 1回のチェックで表示する最大件数
var max=1;
// 10分間隔でチェック
var interval = 10;//10*60;
// privmsgで発言
var privmsg = false;
// デバッグ用
var debug= true; //false;
////////////////////////////////////////
var ServerXMLHTTP = getServerXMLHTTP();
var DOMDocument = getDOMDocument();
var rss_log={};
function event::onLoad(){
log(version + " (" + GetScriptEngineInfo()+")");
for(var url in rss_urls){
try{
if(debug) log("load:"+url);
rss_load(url);
}catch( e ){
log( "error:" + e );
}
}
setTimeout(rss_check_all, interval*1000);
}
function rss_check_all(){
setTimeout(rss_check_all, interval*1000);
for(var url in rss_urls){
try{
if(debug) log("check:"+url);
rss_check(url);
}catch( e ){
log( "error:" + e );
}
}
}
function rss_check(url){
if(! rss_log[url]) rss_log[url]={};
var xmlDoc = new ActiveXObject(DOMDocument);
if(!xmlDoc) return false;
xmlDoc.async = true;
xmlDoc.onreadystatechange =function(){
if (xmlDoc.readyState == 4){
if(xmlDoc.parseError.errorCode == 0) {
var rss = xml2array(xmlDoc);
var btime = Math.floor((new Date().getTime()-24*60*60000)/1000);
var c=0;
if(debug) log("hit:"+rss.list.length);
for(var i =0; rss.list[i] != null ; i++){
var r = rss.list[i];
if(debug && i == 0){
var t = new Date(r.time*1000).toLocaleString();
log( "first:"+ r.title+ " "+ r.link+" "+ t);
}
if( (match[url] && ! r.title.match( match[url]) )
|| ( unmatch[url] && r.title.match( unmatch[url] ) ) )
continue;
if(r.time < btime ||
(rss_log[url][r.link] && rss_log[url][r.link].title == r.title && rss_log[url][r.link].time == r.time)) continue;
rss_log[url][r.link]={};
rss_log[url][r.link].title=r.title;
rss_log[url][r.link].time =r.time;
if( ++c > max ) continue;
var t = new Date(r.time*1000).toLocaleString();
r.title = r.title.replace(/\s+/g," ");
if(get_loc[url]){
if(privmsg){
get_location(r.link,"privmsg "+ rss_urls[url] +" "+ r.title +" <url> "+ t);
}else{
get_location(r.link,"notice "+ rss_urls[url] +" "+ r.title +" <url> "+ t);
}
}else{
if(privmsg){
sendraw("privmsg "+ rss_urls[url] +" "+ r.title +" "+ r.link +" "+ t);
}else{
//send( rss_urls[url], r.title+ " "+ r.link+" "+ t);
send( rss_urls[url], "<bold><color red>新着<stop><bold><color green>フィードです!<stop>: " + r.title+ " "+ r.link+" "+ t);
}
}
}
var logs = rss_log[url];
var c=0;
for(var u in logs){
c++;
if( logs[u].time < btime ){
if(debug) log( "DELETE:" + logs[u].title+ " "+ u);
delete logs[u];
}
}
if(debug) log( "rss_log:" + c);
}
xmlDoc="";
}
};
xmlDoc.load(url);
}
function get_location(url , text){
if(debug) log( "get_loc:" + url);
var xmlhttp = new ActiveXObject(ServerXMLHTTP);
if (! xmlhttp) return false;
xmlhttp.setTimeouts(5*1000,5*1000,15*1000,15*1000);//タイムアウト15秒ぐらい。
xmlhttp.onreadystatechange = function() {
if (xmlhttp.readyState >= 3 ) {
var location = xmlhttp.getOption(-1);
if(location.match(/http/)) url = location;
sendraw(text.replace(/<url>/,url));
if(xmlhttp.readyState < 4) xmlhttp.abort();
xmlhttp="";
}
}
xmlhttp.open("GET", url , true);
xmlhttp.setRequestHeader("Range","bytes=0-32768");//対応していれば取得するのは32kbまで。
xmlhttp.setRequestHeader("User-Agent","Mozilla/5.0 (compatible; rss_check.js;)");
xmlhttp.send("");
}
function rss_load(url){
if(! rss_log[url]) rss_log[url]={};
var xmlDoc = new ActiveXObject(DOMDocument);
if(!xmlDoc) return false;
xmlDoc.async = true;
xmlDoc.onreadystatechange =function(){
if (xmlDoc.readyState == 4){
if (xmlDoc.parseError.errorCode == 0) {
var rss = xml2array(xmlDoc);
var btime = Math.floor((new Date().getTime()-24*60*60000)/1000);
if(debug) log("hit:"+rss.list.length);
for(var i =0; rss.list[i] != null ; i++){
var r = rss.list[i];
if(debug && i == 0){
var t = new Date(r.time*1000).toLocaleString();
log( "first:"+ r.title+ " "+ r.link+" "+ t);
}
if( (match[url] && ! r.title.match( match[url]) )
|| ( unmatch[url] && r.title.match( unmatch[url] ) ) )
continue;
if( r.time < btime ) continue;
rss_log[url][r.link]={};
rss_log[url][r.link].title=r.title;
rss_log[url][r.link].time =r.time;
}
}
xmlDoc="";
}
};
xmlDoc.load(url);
}
function pubDate(str){
return Math.floor(new Date(str).getTime() / 1000);
}
function w3c2time(str){
var date = str.split(/[-+:TZ]/);
if(date){
var s = Date.UTC(date[0], date[1]?date[1] - 1:0,date[2],date[3],date[4],date[5]);
if(date[6]||date[7])s -=(date[6]*60+(date[7]-0))*(str.match(/\+\d\d:\d\d/)?60000:-60000);
return Math.floor(s/1000);
}
return 0;
}
function xml2array(xmlDoc){
var root = xmlDoc.documentElement;
var urlcheck={};
var type = root.nodeName;
var data = {ch:{} , list:[]};
if(type.match(/rss/i)){
root = root.getElementsByTagName("channel");
if(!root.length)return 0;
root = root[0];
for(var i=0; root.childNodes[i]!=null; i++){
switch (root.childNodes[i].nodeName) {
case 'title':
data.ch.title = root.childNodes[i].text;
break;
case 'link':
data.ch.link = root.childNodes[i].text;
break;
case 'pubDate':
data.ch.time = pubDate(root.childNodes[i].text);
break;
case 'dc:date':
data.ch.time = w3c2time(root.childNodes[i].text);
break;
case 'item':
var item={};
var node = root.childNodes[i];
for(var j=0; node.childNodes[j]!=null; j++){
switch (node.childNodes[j].nodeName) {
case 'title':
item.title = node.childNodes[j].text;
break;
case 'link':
item.link = node.childNodes[j].text;
break;
case 'pubDate':
item.time = pubDate(node.childNodes[j].text);
break;
case 'dc:date':
item.time = w3c2time(node.childNodes[j].text);
}
}
if(item && ! urlcheck[item.link] ) data.list.push(item);
urlcheck[item.link]=1;
break;
}
}
}else if( type.match(/rdf/i) ){
for(var i=0; root.childNodes[i]!=null; i++){
switch (root.childNodes[i].nodeName.toLowerCase()) {
case 'channel':
var node = root.childNodes[i];
for(var j=0; node.childNodes[j]!=null; j++){
switch (node.childNodes[j].nodeName.toLowerCase()) {
case 'title':
data.ch.title = node.childNodes[j].text;
break;
case 'link':
data.ch.link = node.childNodes[j].text;
break;
case 'dc:date':
data.ch.time = w3c2time(node.childNodes[j].text);
break;
}
}
break;
case 'item':
var item={};
var node = root.childNodes[i];
for(var j=0; node.childNodes[j]!=null; j++){
switch (node.childNodes[j].nodeName.toLowerCase()) {
case 'title':
item.title = node.childNodes[j].text;
break;
case 'link':
item.link = node.childNodes[j].text;
break;
case 'dc:date':
item.time = w3c2time(node.childNodes[j].text);
break;
}
}
if(item && ! urlcheck[item.link] ) data.list.push(item);
urlcheck[item.link]=1;
break;
}
}
}else if(type.match(/feed/i)){
for(var i=0; root.childNodes[i]!=null; i++){
switch (root.childNodes[i].nodeName.toLowerCase()) {
case 'title':
data.ch.title = root.childNodes[i].text;
break;
case 'link':
if( root.childNodes[i].getAttribute("rel") == "alternate")
data.ch.link = root.childNodes[i].getAttribute("href");
break;
case 'modified':
data.ch.time = w3c2time(root.childNodes[i].text);
break;
case 'entry':
var item={};
var node = root.childNodes[i];
for(var j=0; node.childNodes[j]!=null; j++){
switch (node.childNodes[j].nodeName.toLowerCase()) {
case 'title':
item.title = node.childNodes[j].text;
break;
case 'link':
if( node.childNodes[j].getAttribute("rel") == "alternate")
item.link = node.childNodes[j].getAttribute("href");
break;
case 'modified':
item.time = w3c2time(node.childNodes[j].text);
break;
}
}
if(item && ! urlcheck[item.link] ) data.list.push(item);
urlcheck[item.link]=1;
break;
}
}
}
return data;
}
function getServerXMLHTTP(){
var list=["Msxml2.ServerXMLHTTP.6.0", "Msxml2.ServerXMLHTTP.4.0", "Msxml2.ServerXMLHTTP.3.0", "Msxml2.ServerXMLHTTP" ];
for (var i = 0; i < list.length; i++) {
try {
new ActiveXObject(list[i]);
if(debug)log(list[i])
return list[i];
}
catch (e) {}
}
return null;
}
function getDOMDocument(){
var list=["Msxml2.DOMDocument.6.0", "Msxml2.DOMDocument.4.0", "Msxml2.DOMDocument.3.0", "Msxml2.DOMDocument" ];
for (var i = 0; i < list.length; i++) {
try {
new ActiveXObject(list[i]);
if(debug)log(list[i])
return list[i];
}
catch (e) {}
}
return null;
}
//JScriptのバージョン
function GetScriptEngineInfo(){
var s;
s = ""; // Build string with necessary info.
s += ScriptEngine() + " Version ";
s += ScriptEngineMajorVersion() + ".";
s += ScriptEngineMinorVersion() + ".";
s += ScriptEngineBuildVersion();
return(s);
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment