#!/usr/bin/perl # smlnk-irc.pl by John Leslie # # IRC proxy for www.smLNK.com # Will convert a single URL and exit if an argument is given # Updated by Jonathon Marshall # # New version of smLNK now supports clients on a seperate # script for easier integration # # Updated again by Kyle Christensen # Made the bot wreply to CTCP PING & VERSION requests, and # watch in the defined channel for long urls to shorten # # I also changed the url matching so if the bot is watching # a channel it can glob a url out of a line of text, and not # require a user to paste a url on a seperate line to get a # shortened url. # # Oh and I changed the regexp so it only smlnk's urls > than # 50 characters, I don't see too much of a point in smlnk'ing # anything shorter if it doesn't wrap in my terminal windows. # # Requires Net::IRC and LWP::UserAgent use strict; use LWP::UserAgent; use vars qw ( %CONF $UA $RECONNECTS ); my $version = "smLNK IRC Bot : version 2.0"; %CONF = (Nick=>'ln-s', Server=>'irc2.secsup.org', Port=>6667, Ircname=>'bite my shiny metal ass', MaxReconnects=>5, Channel=>'#rit'); if ($ARGV[0]) { print &get_smlnk($ARGV[0]), "\n"; exit(0); } else { ⊥ } sub bot { my ($irc, $conn); require Net::IRC; # so we can run from the cmdline without $irc = new Net::IRC; $conn = $irc->newconn(%CONF) or die ("Couldn't connect to $CONF{Server}\n"); $conn->add_global_handler(376, \&on_connect); $conn->add_global_handler('disconnect', \&on_disconnect); $conn->add_handler('cversion', \&on_cversion); $conn->add_handler('cping', \&on_ping); $conn->add_handler('msg', \&on_msg); $conn->add_handler('public', \&on_public); $irc->start; exit(0); } # get_smlink($url) return an smlnk'd URL, the site's error, or undef sub get_smlnk { my ($req, $url, $data); my ($url) = @_; $UA ||= LWP::UserAgent->new(timeout => 15) or return; $req = $UA->post("http://smlnk.com/client.php", {url => $url}) or return; return unless ($req->is_success); $data = $req->content; return $data; } # Net::IRC Handlers sub on_connect { my ($this) = @_; if ($CONF{Channel}) { print "Joining $CONF{Channel}\n"; $this->join($CONF{Channel}); } } sub on_ping { my ($self, $event) = @_; my $nick = $event->nick; $self->ctcp_reply($nick, join(' ', ('PING', $event->args))); print "Ping request from $nick\n"; } sub on_cversion { my ($self, $event) = @_; my $nick = $event->nick; $self->ctcp_reply($nick, join(' ', ($event->args), $version)); print "Version request from $nick\n"; } sub on_public { my $reply; my ($self, $event) = @_; my @to = $event->to; my ($arg) = ($event->args); if ($arg =~ /((https?|ftp):\/\/\S{50,})/) { $reply = &get_smlnk($1) || "Error smlnk'ing $1"; $reply =~ s/^\s+//; print "smLNK ($CONF{Channel}): $1 -> $reply\n"; $self->privmsg($CONF{Channel}, "$reply") if ($CONF{Channel}); } return; } sub on_msg { my ($nick, $msg, $reply); my ($this, $event) = @_; $nick = $event->nick; ($msg) = $event->args; if ($msg =~ /.+:\/\/.+/) { $reply = &get_smlnk($msg) || "Error smlnk'ing $msg"; } else { $reply = "Invalid URL"; } $this->privmsg($nick, $reply); #if ($reply =~ /^(http)/) { # $this->privmsg($CONF{Channel}, "smLNK ($nick): $msg -> $reply") if ($CONF{Channel}); #} print "smLNK ($nick): $msg -> $reply\n"; return; } sub on_disconnect { my ($this, $event) = @_; print "Disconnected from ", $event->from(), " (", ($event->args())[0], ").\n"; if (++$RECONNECTS >= $CONF{MaxReconnects}) { print "Reached maximum reconnects ($RECONNECTS), exiting\n"; exit(1); } else { print "Attempting to reconnect...\n"; $this->connect(); } }