Site updated at 2014-03-19 15:05:21 UTC

gh-pages
joesepi 10 years ago
parent 72cd54dff8
commit 2a343506e0

@ -4,7 +4,7 @@
<title><![CDATA[NVD3]]></title>
<link href="http://nvd3.org//atom.xml" rel="self"/>
<link href="http://nvd3.org//"/>
<updated>2014-03-13T14:21:37-04:00</updated>
<updated>2014-03-19T10:58:55-04:00</updated>
<id>http://nvd3.org//</id>
<author>
<name><![CDATA[Novus Partners]]></name>
@ -13,6 +13,79 @@
<generator uri="http://octopress.org/">Octopress</generator>
<entry>
<title type="html"><![CDATA[Nvd3 Issues Triage]]></title>
<link href="http://nvd3.org//blog/2014/03/nvd3-issues-triage/"/>
<updated>2014-03-19T10:42:43-04:00</updated>
<id>http://nvd3.org//blog/2014/03/nvd3-issues-triage</id>
<content type="html"><![CDATA[<p>Novus is committed to its open source projects and committed to the community that has grown around these projects. In an effort to tame the recent build-up of issues and pull requests, we would like to outline our appraoch to tackling this accumulation in the short term as well as how we will continue to manage the project&rsquo;s growth in the future.</p>
<hr />
<h3>Short term</h3>
<p>Our first priority is to tame the pile of issues and PRs that have recently accumulated. To do so, we will categorize them accordingly:</p>
<ul>
<li><strong>Out of Date</strong>
For out of date issues and pull requests, we will close the stale request with a brief explanation.</li>
<li><strong>Support</strong>
When an issue falls under the Support banner, we will provide a short answer that we hope is helpful. We may also suggest posting the issue to Stack Overflow to discuss the issue further.</li>
<li><strong>Bug in Refactor</strong>
When the issue is a repeatable bug, we will work with the commenter to fix the matter and hope to resolve the issue without much delay.</li>
<li><strong>Feature Enhancement</strong> (Small improvements in existing, refactored code)
[work with commenter to add improvement in refactored code]</li>
<li><strong>New Features</strong> (Large improvements, eg new chart types)
Our expectation with new features will be to move them to the roadmap and prioritize them accordingly.</li>
</ul>
<p>With this approach, we expect to be able to address what needs to be done immediately and prioritize everything else.</p>
<hr />
<h3>Long term</h3>
<p>In the long term, we would like to take a more holistic approach that can allow us to not only shrink the amount of issues and PRs, but also to potentially expand the group that would help us manicure this garden.</p>
<p>Below is how we will break out the issues, with some overlap from above:</p>
<ul>
<li><strong>Bug</strong>: Request steps to repeat the issue and triage accordingly</li>
<li><strong>Improvement</strong>: Request feature tests and implementation and/or triage accordingly</li>
<li><strong>Feature</strong>: Triage the request and work with requester to break up the work into small, deliverable pieces and find a shepherd for the feature deliverable</li>
</ul>
<h4>Triage levels</h4>
<ul>
<li><strong>Duplicate</strong>: closed immediately; with link to other issue</li>
<li><strong>Support</strong>: closed immediately; Attempt a short answer/explanation, suggest Stack Overflow for a deeper exploration</li>
<li><strong>Fix</strong>: Small task, Shouldn&rsquo;t take more than half a day.</li>
<li><strong>Improvement</strong>: Smaller tasks; Easily completable with a couple days&#8217; solid work.</li>
<li><strong>Feature</strong>: Larger tasks; Takes at least a week, probably needs serious planning before development.</li>
</ul>
<h4>Additional tags</h4>
<ul>
<li><strong>Intro</strong>: Represents a good entry point to some part of the project</li>
<li><strong>Octopages</strong>: Documentation</li>
<li><strong>Out of date</strong>: ticket is more than 3 months old and is not automatically mergeable</li>
<li><strong>Won&rsquo;t fix</strong>: discretionary; thank you but does not align with project direction or aesthetics</li>
</ul>
<p>We have added these as labels to Github and have been applying them to the backlog of issues and requests.</p>
<p>As I mentioned, we hope to not only work with the community more in the future but also to bring some trusted developers into the fold to help us evolve nvd3 forward into the future.</p>
<p>Thanks.</p>
]]></content>
</entry>
<entry>
<title type="html"><![CDATA[The Future of NVD3 - March, 2014]]></title>
<link href="http://nvd3.org//blog/2014/03/state-of-nvd3/"/>

@ -0,0 +1,293 @@
<!DOCTYPE html>
<!--[if IEMobile 7 ]><html class="no-js iem7"><![endif]-->
<!--[if lt IE 9]><html class="no-js lte-ie8"><![endif]-->
<!--[if (gt IE 8)|(gt IEMobile 7)|!(IEMobile)|!(IE)]><!--><html class="no-js" lang="en"><!--<![endif]-->
<head>
<meta charset="utf-8">
<title>Nvd3 Issues Triage - NVD3</title>
<meta name="author" content="Novus Partners">
<meta name="description" content="Novus is committed to its open source projects and committed to the community that has grown around these projects. In an effort to tame the recent &hellip;">
<!-- http://t.co/dKP3o1e -->
<meta name="HandheldFriendly" content="True">
<meta name="MobileOptimized" content="320">
<meta name="viewport" content="width=device-width, initial-scale=1">
<link rel="canonical" href="http://nvd3.org//blog/2014/03/nvd3-issues-triage">
<link href="/favicon.png" rel="icon">
<!-- <link href="/stylesheets/screen.css" media="screen, projection" rel="stylesheet" type="text/css"> -->
<link href="/atom.xml" rel="alternate" title="NVD3" type="application/atom+xml">
<script src="/javascripts/modernizr-2.0.js"></script>
<script src="//ajax.googleapis.com/ajax/libs/jquery/1.9.1/jquery.min.js"></script>
<script>!window.jQuery && document.write(unescape('%3Cscript src="./javascripts/libs/jquery.min.js"%3E%3C/script%3E'))</script>
<script src="/javascripts/octopress.js" type="text/javascript"></script>
<!--Fonts from Google"s Web font directory at http://google.com/webfonts -->
<link href="//fonts.googleapis.com/css?family=PT+Serif:regular,italic,bold,bolditalic" rel="stylesheet" type="text/css">
<link href="//fonts.googleapis.com/css?family=PT+Sans:regular,italic,bold,bolditalic" rel="stylesheet" type="text/css">
<link href="/assets/css/bootstrap.css" rel="stylesheet">
<style type="text/css">
body {
padding-top: 60px;
padding-bottom: 40px;
}
.statement_para {
font-size: 14pt;
line-height: 120%;
width: 60%;
text-align: justify;
text-justify: distribute;
margin: 10px auto;
margin-bottom: 30px;
}
</style>
<link href="/assets/css/common.css" rel="stylesheet">
<link href="/assets/css/nv.d3.css" rel="stylesheet">
<script src="/assets/js/lib/bootstrap.min.js"></script>
<script src="/assets/lib/d3.v3.js"></script>
<script src="/assets/js/nv.d3.js"></script>
<script src="/assets/js/data/stream_layers.js"></script>
<script src="/assets/js/page/index.js"></script>
<script type="text/javascript">
var _gaq = _gaq || [];
_gaq.push(['_setAccount', 'UA-33058059-1']);
_gaq.push(['_trackPageview']);
(function() {
var ga = document.createElement('script'); ga.type = 'text/javascript'; ga.async = true;
ga.src = ('https:' == document.location.protocol ? 'https://ssl' : 'http://www') + '.google-analytics.com/ga.js';
var s = document.getElementsByTagName('script')[0]; s.parentNode.insertBefore(ga, s);
})();
</script>
</head>
<body >
<nav role="navigation"> <div class="navbar navbar-inverse navbar-fixed-top">
<div class="navbar-inner">
<div class="container">
<a class="btn btn-navbar" data-toggle="collapse" data-target=".nav-collapse">
<span class="icon-bar"></span>
<span class="icon-bar"></span>
<span class="icon-bar"></span>
</a>
<a class="brand" href="/index.html">NVD3.js</a>
<div class="nav-collapse">
<ul class="nav">
<li class="active"><a href="/index.html"><i class="icon-white icon-home"></i> Home</a></li>
<li><a href="/examples/index.html"><i class="icon-white icon-picture"></i> Examples</a></li>
<li><a href="/livecode/index.html"><i class="icon-white icon-play-circle"></i> Live Code</a></li>
<li><a href="http://github.com/novus/nvd3"><i class="icon-white icon-list-alt"></i> Source</a></li>
<li><a href="/blog/archives/"><i class="icon-white icon-book"></i> Blog</a></li>
</ul>
<ul class="nav pull-right">
<li><p class="navbar-text"><i class="icon-white icon-download"></i> Downloads:</p></li>
<li>
<div class="btn-group">
<a class="btn btn-small btn-primary" href="https://github.com/novus/nvd3/zipball/master">ZIP</a>
<a class="btn btn-small btn-primary" href="https://github.com/novus/nvd3/tarball/master">TAR.GZ</a>
</div>
</li>
</ul>
</div>
</div>
</div>
</div>
</nav>
<div class="container with-3d-shadow with-transitions">
<div>
<article class="hentry" role="article">
<header>
<h1 class="entry-title">Nvd3 Issues Triage</h1>
<p class="meta">
<time datetime="2014-03-19T10:42:43-04:00" pubdate data-updated="true">Mar 19<span>th</span>, 2014</time>
</p>
</header>
<div class="entry-content"><p>Novus is committed to its open source projects and committed to the community that has grown around these projects. In an effort to tame the recent build-up of issues and pull requests, we would like to outline our appraoch to tackling this accumulation in the short term as well as how we will continue to manage the project&rsquo;s growth in the future.</p>
<hr />
<h3>Short term</h3>
<p>Our first priority is to tame the pile of issues and PRs that have recently accumulated. To do so, we will categorize them accordingly:</p>
<ul>
<li><strong>Out of Date</strong>
For out of date issues and pull requests, we will close the stale request with a brief explanation.</li>
<li><strong>Support</strong>
When an issue falls under the Support banner, we will provide a short answer that we hope is helpful. We may also suggest posting the issue to Stack Overflow to discuss the issue further.</li>
<li><strong>Bug in Refactor</strong>
When the issue is a repeatable bug, we will work with the commenter to fix the matter and hope to resolve the issue without much delay.</li>
<li><strong>Feature Enhancement</strong> (Small improvements in existing, refactored code)
[work with commenter to add improvement in refactored code]</li>
<li><strong>New Features</strong> (Large improvements, eg new chart types)
Our expectation with new features will be to move them to the roadmap and prioritize them accordingly.</li>
</ul>
<p>With this approach, we expect to be able to address what needs to be done immediately and prioritize everything else.</p>
<hr />
<h3>Long term</h3>
<p>In the long term, we would like to take a more holistic approach that can allow us to not only shrink the amount of issues and PRs, but also to potentially expand the group that would help us manicure this garden.</p>
<p>Below is how we will break out the issues, with some overlap from above:</p>
<ul>
<li><strong>Bug</strong>: Request steps to repeat the issue and triage accordingly</li>
<li><strong>Improvement</strong>: Request feature tests and implementation and/or triage accordingly</li>
<li><strong>Feature</strong>: Triage the request and work with requester to break up the work into small, deliverable pieces and find a shepherd for the feature deliverable</li>
</ul>
<h4>Triage levels</h4>
<ul>
<li><strong>Duplicate</strong>: closed immediately; with link to other issue</li>
<li><strong>Support</strong>: closed immediately; Attempt a short answer/explanation, suggest Stack Overflow for a deeper exploration</li>
<li><strong>Fix</strong>: Small task, Shouldn&rsquo;t take more than half a day.</li>
<li><strong>Improvement</strong>: Smaller tasks; Easily completable with a couple days&#8217; solid work.</li>
<li><strong>Feature</strong>: Larger tasks; Takes at least a week, probably needs serious planning before development.</li>
</ul>
<h4>Additional tags</h4>
<ul>
<li><strong>Intro</strong>: Represents a good entry point to some part of the project</li>
<li><strong>Octopages</strong>: Documentation</li>
<li><strong>Out of date</strong>: ticket is more than 3 months old and is not automatically mergeable</li>
<li><strong>Won&rsquo;t fix</strong>: discretionary; thank you but does not align with project direction or aesthetics</li>
</ul>
<p>We have added these as labels to Github and have been applying them to the backlog of issues and requests.</p>
<p>As I mentioned, we hope to not only work with the community more in the future but also to bring some trusted developers into the fold to help us evolve nvd3 forward into the future.</p>
<p>Thanks.</p>
</div>
<footer>
<p class="meta">
<span class="byline author vcard">Posted by <span class="fn">joesepi <sepi@joesepi.com></span></span>
<time datetime="2014-03-19T10:42:43-04:00" pubdate data-updated="true">Mar 19<span>th</span>, 2014</time>
</p>
<div class="sharing">
<a href="//twitter.com/share" class="twitter-share-button" data-url="http://nvd3.org//blog/2014/03/nvd3-issues-triage/" data-via="" data-counturl="http://nvd3.org//blog/2014/03/nvd3-issues-triage/" >Tweet</a>
<div class="g-plusone" data-size="medium"></div>
</div>
<p class="meta">
<a class="basic-alignment left" href="/blog/2014/03/state-of-nvd3/" title="Previous Post: The Future of NVD3 - March, 2014">&laquo; The Future of NVD3 - March, 2014</a>
</p>
</footer>
</article>
</div>
<footer role="contentinfo"><p>
Copyright &copy; 2014 - <a href="http://www.novus.com">Novus Partners</a> -
<span class="credit">Powered by <a href="http://octopress.org">Octopress</a></span>
</p>
</footer>
<script type="text/javascript">
(function() {
var script = document.createElement('script'); script.type = 'text/javascript'; script.async = true;
script.src = 'https://apis.google.com/js/plusone.js';
var s = document.getElementsByTagName('script')[0]; s.parentNode.insertBefore(script, s);
})();
</script>
<script type="text/javascript">
(function(){
var twitterWidgets = document.createElement('script');
twitterWidgets.type = 'text/javascript';
twitterWidgets.async = true;
twitterWidgets.src = '//platform.twitter.com/widgets.js';
document.getElementsByTagName('head')[0].appendChild(twitterWidgets);
})();
</script>
</div>
</body>
</html>

@ -202,6 +202,8 @@
<p class="meta">
<a class="basic-alignment right" href="/blog/2014/03/nvd3-issues-triage/" title="Next Post: nvd3 issues triage">nvd3 issues triage &raquo;</a>
</p>
</footer>
</article>

@ -9,8 +9,9 @@
<meta name="author" content="Novus Partners">
<meta name="description" content=" Blog Archive 2014 The Future of NVD3 - March, 2014
Mar 12 2014 Recent Posts The Future of NVD3 - March, 2014 ">
<meta name="description" content="Blog Archive 2014 Nvd3 Issues Triage
Mar 19 2014 The Future of NVD3 - March, 2014
Mar 12 2014 Recent Posts Nvd3 Issues Triage The Future of NVD3 - &hellip;">
<!-- http://t.co/dKP3o1e -->
@ -124,6 +125,16 @@ Mar 12 2014 Recent Posts The Future of NVD3 - March, 2014 ">
<h2>2014</h2>
<article>
<h1><a href="/blog/2014/03/nvd3-issues-triage/">Nvd3 Issues Triage</a></h1>
<time datetime="2014-03-19T10:42:43-04:00" pubdate><span class='month'>Mar</span> <span class='day'>19</span> <span class='year'>2014</span></time>
</article>
<article>
<h1><a href="/blog/2014/03/state-of-nvd3/">The Future of NVD3 - March, 2014</a></h1>
@ -145,6 +156,10 @@ Mar 12 2014 Recent Posts The Future of NVD3 - March, 2014 ">
<h1>Recent Posts</h1>
<ul id="recent_posts">
<li class="post">
<a href="/blog/2014/03/nvd3-issues-triage/">Nvd3 Issues Triage</a>
</li>
<li class="post">
<a href="/blog/2014/03/state-of-nvd3/">The Future of NVD3 - March, 2014</a>
</li>

@ -2,74 +2,78 @@
<urlset xmlns='http://www.sitemaps.org/schemas/sitemap/0.9'>
<url>
<loc>http://nvd3.org//blog/2014/03/state-of-nvd3/</loc>
<lastmod>2014-03-13T11:50:48-04:00</lastmod>
<lastmod>2014-03-19T10:53:12-04:00</lastmod>
</url>
<url>
<loc>http://nvd3.org//blog/2014/03/nvd3-issues-triage/</loc>
<lastmod>2014-03-19T10:57:55-04:00</lastmod>
</url>
<url>
<loc>http://nvd3.org//blog/archives/</loc>
<lastmod>2014-03-13T11:50:48-04:00</lastmod>
<lastmod>2014-03-19T10:57:55-04:00</lastmod>
</url>
<url>
<loc>http://nvd3.org//examples/bullet.html</loc>
<lastmod>2014-03-12T18:13:30-04:00</lastmod>
<lastmod>2014-03-17T10:25:34-04:00</lastmod>
</url>
<url>
<loc>http://nvd3.org//examples/cumulativeLine.html</loc>
<lastmod>2014-03-12T18:13:30-04:00</lastmod>
<lastmod>2014-03-17T10:25:34-04:00</lastmod>
</url>
<url>
<loc>http://nvd3.org//examples/discreteBar.html</loc>
<lastmod>2014-03-12T18:13:30-04:00</lastmod>
<lastmod>2014-03-17T10:25:34-04:00</lastmod>
</url>
<url>
<loc>http://nvd3.org//examples/indentedtree.html</loc>
<lastmod>2014-03-12T18:13:30-04:00</lastmod>
<lastmod>2014-03-17T10:25:34-04:00</lastmod>
</url>
<url>
<loc>http://nvd3.org//examples/</loc>
<lastmod>2014-03-13T11:50:48-04:00</lastmod>
<lastmod>2014-03-19T10:57:55-04:00</lastmod>
</url>
<url>
<loc>http://nvd3.org//examples/line.html</loc>
<lastmod>2014-03-12T18:13:30-04:00</lastmod>
<lastmod>2014-03-17T10:25:34-04:00</lastmod>
</url>
<url>
<loc>http://nvd3.org//examples/linePlusBar.html</loc>
<lastmod>2014-03-12T18:13:30-04:00</lastmod>
<lastmod>2014-03-17T10:25:34-04:00</lastmod>
</url>
<url>
<loc>http://nvd3.org//examples/lineWithFocus.html</loc>
<lastmod>2014-03-12T18:13:30-04:00</lastmod>
<lastmod>2014-03-17T10:25:34-04:00</lastmod>
</url>
<url>
<loc>http://nvd3.org//examples/multiBar.html</loc>
<lastmod>2014-03-12T18:13:30-04:00</lastmod>
<lastmod>2014-03-17T10:25:34-04:00</lastmod>
</url>
<url>
<loc>http://nvd3.org//examples/multiBarHorizontal.html</loc>
<lastmod>2014-03-12T18:13:30-04:00</lastmod>
<lastmod>2014-03-17T10:25:34-04:00</lastmod>
</url>
<url>
<loc>http://nvd3.org//examples/pie.html</loc>
<lastmod>2014-03-12T18:13:30-04:00</lastmod>
<lastmod>2014-03-17T10:25:34-04:00</lastmod>
</url>
<url>
<loc>http://nvd3.org//examples/scatter.html</loc>
<lastmod>2014-03-12T18:13:30-04:00</lastmod>
<lastmod>2014-03-17T10:25:34-04:00</lastmod>
</url>
<url>
<loc>http://nvd3.org//examples/stackedArea.html</loc>
<lastmod>2014-03-12T18:13:30-04:00</lastmod>
<lastmod>2014-03-17T10:25:34-04:00</lastmod>
</url>
<url>
<loc>http://nvd3.org//</loc>
<lastmod>2014-03-13T11:50:48-04:00</lastmod>
<lastmod>2014-03-19T10:57:55-04:00</lastmod>
</url>
<url>
<loc>http://nvd3.org//livecode/</loc>
<lastmod>2014-03-13T11:50:48-04:00</lastmod>
<lastmod>2014-03-19T10:57:55-04:00</lastmod>
</url>
<url>
<loc>http://nvd3.org//robots.txt</loc>
<lastmod>2014-03-12T18:13:30-04:00</lastmod>
<lastmod>2014-03-17T10:25:34-04:00</lastmod>
</url>
</urlset>

File diff suppressed because one or more lines are too long

@ -0,0 +1,51 @@
[10:26:44] [connected at Mon Mar 17 10:26:44 2014]
[10:26:50] [I have joined #nvd3]
[10:26:59] <davidsouther1> twistedbot: hello
[10:26:59] <twistedbot> davidsouther1: I am a log bot
[10:27:09] davidsouther1 is now known as southerd
[10:28:57] [disconnected at Mon Mar 17 10:28:57 2014]
[10:29:01] [connected at Mon Mar 17 10:29:01 2014]
[10:29:07] [I have joined #nvd3]
[10:29:31] transcriptbot is now known as Guest35483
[10:33:01] <southerd> Guest35483: Hello
[10:33:25] <southerd> Guest35483: hello
[10:33:39] [disconnected at Mon Mar 17 10:33:39 2014]
[10:33:45] [connected at Mon Mar 17 10:33:45 2014]
[10:34:42] [disconnected at Mon Mar 17 10:34:42 2014]
[10:34:42] [connected at Mon Mar 17 10:34:42 2014]
[10:35:14] [disconnected at Mon Mar 17 10:35:14 2014]
[10:35:17] [connected at Mon Mar 17 10:35:17 2014]
[10:35:39] [disconnected at Mon Mar 17 10:35:39 2014]
[10:35:41] [connected at Mon Mar 17 10:35:41 2014]
[10:35:50] [I have joined #nvd3]
[10:36:15] <southerd> nvd3_sten: hello
[10:36:15] <nvd3_sten> southerd: I am a log bot
[10:37:32] <robinhu> sup Log Bot.
[10:43:16] <joesepi> Hello Log Bot.
[13:01:26] [disconnected at Mon Mar 17 13:01:26 2014]
[13:01:26] [connected at Mon Mar 17 13:01:26 2014]
[13:01:39] [I have joined #nvd3]
[13:23:38] <JFSIII> Hello, Log Bot and others
[13:28:47] <davidsouther> Woot.
[13:28:53] <davidsouther> I should replace it with something smarter
[13:29:21] <davidsouther> hubot, probably
[14:03:02] [disconnected at Mon Mar 17 14:03:02 2014]
[14:03:02] [connected at Mon Mar 17 14:03:02 2014]
[14:03:18] [I have joined #nvd3]
[14:03:52] davidsouther is now known as southerd
[14:07:01] [disconnected at Mon Mar 17 14:07:01 2014]
[14:07:01] [connected at Mon Mar 17 14:07:01 2014]
[14:07:07] [I have joined #nvd3]
[14:10:33] <southerd> JFSIII: joesepi is typing up some triage guidelines for moving forward with cleaning out the Github backlog
[14:11:05] <southerd> At the same time, I'm typing up some notes on the refactor going on in the (poorly named) "Canvas" branch
[14:11:11] <JFSIII> OK, great
[14:12:31] <JFSIII> I must confess I didn't get around to making notes on the code. This weekend, I spent my free hours moving my work project from grunt to a simple node.js build script
[14:13:04] <JFSIII> but I'm pretty familiar with the code. I've been using it (and reading / patching models) for 9+ months.
[14:21:46] <southerd> Yeah, at this point the "Canvas" refactor is just pulling out the most commonly repeated bits of code
[14:22:10] <southerd> Specifically, margins & inserting the wrap-classed DOM nodes.
[14:24:41] <southerd> With that, we should also have tests for all the charts, and find a way to automate them (rather than start a static server in the root folder and click through `tests/`
[14:25:51] <southerd> I'd also like to see us move away from the getter/setter mechanism - I'd almost go so far as to call it an anti pattern, but it's so integral to the way d3 handles object state that might not be possible
[14:26:31] <southerd> And finally, I want to see a more composite approach to creating complex charts
[16:39:53] <southerd> hey there, novusTyler
[16:40:15] <novusTyler> hi
[17:10:32] [disconnected at Mon Mar 17 17:10:32 2014]

@ -0,0 +1,164 @@
# Copyright (c) Twisted Matrix Laboratories.
# See LICENSE for details.
"""
An example IRC log bot - logs a channel's events to a file.
If someone says the bot's name in the channel followed by a ':',
e.g.
<foo> logbot: hello!
the bot will reply:
<logbot> foo: I am a log bot
Run this script with two arguments, the channel name the bot should
connect to, and file to log to, e.g.:
$ python ircLogBot.py test test.log
will log channel #test to the file 'test.log'.
To run the script:
$ python ircLogBot.py <channel> <file>
"""
# twisted imports
from twisted.words.protocols import irc
from twisted.internet import reactor, protocol
from twisted.python import log
# system imports
import time, sys
class MessageLogger:
"""
An independent logger class (because separation of application
and protocol logic is a good thing).
"""
def __init__(self, file):
self.file = file
def log(self, message):
"""Write a message to the file."""
timestamp = time.strftime("[%H:%M:%S]", time.localtime(time.time()))
self.file.write('%s %s\n' % (timestamp, message))
self.file.flush()
def close(self):
self.file.close()
class LogBot(irc.IRCClient):
"""A logging IRC bot."""
nickname = "nvd3_sten"
def connectionMade(self):
irc.IRCClient.connectionMade(self)
self.logger = MessageLogger(open(self.factory.filename, "a"))
self.logger.log("[connected at %s]" %
time.asctime(time.localtime(time.time())))
def connectionLost(self, reason):
irc.IRCClient.connectionLost(self, reason)
self.logger.log("[disconnected at %s]" %
time.asctime(time.localtime(time.time())))
self.logger.close()
# callbacks for events
def signedOn(self):
"""Called when bot has succesfully signed on to server."""
self.join(self.factory.channel)
def joined(self, channel):
"""This will get called when the bot joins the channel."""
self.logger.log("[I have joined %s]" % channel)
msg = "Hello. I am taking a transcript of this channel."
self.msg(channel, msg)
def privmsg(self, user, channel, msg):
"""This will get called when the bot receives a message."""
user = user.split('!', 1)[0]
self.logger.log("<%s> %s" % (user, msg))
# Check to see if they're sending me a private message
if channel == self.nickname:
msg = "It isn't nice to whisper! Play nice with the group."
self.msg(user, msg)
return
# Otherwise check to see if it is a message directed at me
if msg.startswith(self.nickname + ":"):
msg = "%s: I am a log bot" % user
self.msg(channel, msg)
self.logger.log("<%s> %s" % (self.nickname, msg))
def action(self, user, channel, msg):
"""This will get called when the bot sees someone do an action."""
user = user.split('!', 1)[0]
self.logger.log("* %s %s" % (user, msg))
# irc callbacks
def irc_NICK(self, prefix, params):
"""Called when an IRC user changes their nickname."""
old_nick = prefix.split('!')[0]
new_nick = params[0]
self.logger.log("%s is now known as %s" % (old_nick, new_nick))
# For fun, override the method that determines how a nickname is changed on
# collisions. The default method appends an underscore.
def alterCollidedNick(self, nickname):
"""
Generate an altered version of a nickname that caused a collision in an
effort to create an unused related name for subsequent registration.
"""
return nickname + '^'
class LogBotFactory(protocol.ClientFactory):
"""A factory for LogBots.
A new protocol instance will be created each time we connect to the server.
"""
def __init__(self, channel, filename):
self.channel = channel
self.filename = filename
def buildProtocol(self, addr):
p = LogBot()
p.factory = self
return p
def clientConnectionLost(self, connector, reason):
"""If we get disconnected, reconnect to server."""
connector.connect()
def clientConnectionFailed(self, connector, reason):
print "connection failed:", reason
reactor.stop()
if __name__ == '__main__':
# initialize logging
log.startLogging(sys.stdout)
# create factory protocol and application
f = LogBotFactory(sys.argv[1], sys.argv[2])
# connect factory to this host and port
reactor.connectTCP("irc.freenode.net", 6667, f)
# run bot
reactor.run()
Loading…
Cancel
Save