From 566f7a16502135cbf3ccd6c2821d7594853b1d65 Mon Sep 17 00:00:00 2001 From: Marius Gavrilescu Date: Sun, 11 Aug 2013 23:15:20 +0300 Subject: [PATCH 1/1] Initial commit --- Changes | 4 + MANIFEST | 6 ++ Makefile.PL | 18 ++++ README | 30 ++++++ lib/POE/Component/IRC/Plugin/Seen.pm | 138 +++++++++++++++++++++++++++ t/POE-Component-IRC-Plugin-Seen.t | 45 +++++++++ 6 files changed, 241 insertions(+) create mode 100644 Changes create mode 100644 MANIFEST create mode 100644 Makefile.PL create mode 100644 README create mode 100644 lib/POE/Component/IRC/Plugin/Seen.pm create mode 100644 t/POE-Component-IRC-Plugin-Seen.t diff --git a/Changes b/Changes new file mode 100644 index 0000000..cdcdfbd --- /dev/null +++ b/Changes @@ -0,0 +1,4 @@ +Revision history for Perl extension POE::Component::IRC::Plugin::Seen. + +0.001 Sun 11 Aug 23:03:40 EEST 2013 + - Initial Release diff --git a/MANIFEST b/MANIFEST new file mode 100644 index 0000000..2621358 --- /dev/null +++ b/MANIFEST @@ -0,0 +1,6 @@ +Changes +Makefile.PL +MANIFEST +README +t/POE-Component-IRC-Plugin-Seen.t +lib/POE/Component/IRC/Plugin/Seen.pm diff --git a/Makefile.PL b/Makefile.PL new file mode 100644 index 0000000..d7c296e --- /dev/null +++ b/Makefile.PL @@ -0,0 +1,18 @@ +use ExtUtils::MakeMaker; + +WriteMakefile( + NAME => 'POE::Component::IRC::Plugin::Seen', + VERSION_FROM => 'lib/POE/Component/IRC/Plugin/Seen.pm', + ABSTRACT_FROM => 'lib/POE/Component/IRC/Plugin/Seen.pm', + AUTHOR => 'Marius Gavrilescu ', + LICENSE => 'perl', + MIN_PERL_VERSION => 5.014000, + PREREQ_PM => { + DB_File => 0, + POE::Component::IRC::Plugin => 0, + IRC::Utils => 0.05, + }, + BUILD_REQUIRES => { + Test::MockObject => 0, + } +); diff --git a/README b/README new file mode 100644 index 0000000..8a9485a --- /dev/null +++ b/README @@ -0,0 +1,30 @@ +POE-Component-IRC-Plugin-Seen version 0.001 +=========================================== + +POE::Component::IRC::Plugin::Seen is a PoCo-IRC plugin that remembers what each person around it did last. + +When somebody sends him a private message of the form 'seen NICKNAME' or somebody says 'botnick: seen NICKNAME' in a channel with the bot, the plugin answers with the last action NICKNAME did. + +INSTALLATION + +To install this module type the following: + + perl Makefile.PL + make + make test + make install + +DEPENDENCIES + +This module requires these other modules and libraries: + +* POE::Component::IRC +* IRC::Utils + +COPYRIGHT AND LICENCE + +Copyright (C) 2013 by Marius Gavrilescu + +This library is free software; you can redistribute it and/or modify +it under the same terms as Perl itself, either Perl version 5.14.2 or, +at your option, any later version of Perl 5 you may have available. diff --git a/lib/POE/Component/IRC/Plugin/Seen.pm b/lib/POE/Component/IRC/Plugin/Seen.pm new file mode 100644 index 0000000..243a24c --- /dev/null +++ b/lib/POE/Component/IRC/Plugin/Seen.pm @@ -0,0 +1,138 @@ +package POE::Component::IRC::Plugin::Seen; + +our $VERSION = 0.001; + +use v5.14; +use strict; +use warnings; + +use DB_File; + +use IRC::Utils qw/lc_irc parse_user/; +use POE::Component::IRC::Plugin qw/PCI_EAT_NONE PCI_EAT_PLUGIN/; + +################################################## + +sub new{ + my $class = shift; + my $self = { @_ }; + + $self->{dbobj} = tie my %db, DB_File => $self->{filename}; + $self->{db} = \%db; + bless $self, $class +} + +sub log_event { + my ($self, $nick, $event) = @_; + my $time = localtime; + $self->{db}->{$nick} = "$time $event"; + $self->{dbobj}->sync; + PCI_EAT_NONE +} + +sub seen { + my ($self, $irc, $nick, $to, $from) = @_; + if (exists $self->{db}->{$nick}) { + $irc->yield(privmsg => $to => "I last saw $nick $self->{db}->{$nick}") + } else { + $irc->yield(privmsg => $to => "I haven't seen $nick") + } + PCI_EAT_PLUGIN +} + +sub PCI_register { + my ($self, $irc) = @_; + $irc->plugin_register($self, SERVER => qw/ctcp_action join part public msg/); + 1 +} + +sub PCI_unregister { 1 } + +sub S_ctcp_action { + my ($self, $irc, $rfullname, $rchannels, $rmessage) = @_; + my $nick = parse_user $$rfullname; + + log_event $self, $nick => "on $$rchannels->[0] doing: * $$rmessage" +} + +sub S_public { + my ($self, $irc, $rfullname, $rchannels, $rmessage) = @_; + my $nick = parse_user $$rfullname; + my $mynick = $irc->nick_name; + + seen $self, $irc, $1, $$rchannels->[0], $nick if $$rmessage =~ /^(?:$mynick [,:])?\s*seen\s+([^ ]+)/x; + log_event $self, $nick => "on $$rchannels->[0] saying $$rmessage" +} + +sub S_join { + my ($self, $irc, $rfullname, $rchannel) = @_; + my $nick = parse_user $$rfullname; + + log_event $self, $nick => "joining $$rchannel" +} + +sub S_part { + my ($self, $irc, $rfullname, $rchannel, $rmessage) = @_; + my $nick = parse_user $$rfullname; + my $msg = $$rmessage ? " with message '$$rmessage'" : ''; + + log_event $self, $nick => "parting $$rchannel$msg" +} + +sub S_msg { + my ($self, $irc, $rfullname, $rtargets, $rmessage) = @_; + my $nick = parse_user $$rfullname; + + seen $self, $irc, $$rmessage, $$rtargets->[0], $nick if $$rmessage =~ /^seen\s+([^ ]+)/ +} + +1; +__END__ + +=head1 NAME + +POE::Component::IRC::Plugin::Seen - PoCo-IRC plugin that remembers seeing people + +=head1 SYNOPSIS + + use POE::Component::IRC::Plugin::Seen; + + my $irc = POE::Component::IRC->spawn; + $irc->plugin_add(Seen => POE::Component::IRC::Plugin::Seen->new(filename => 'mycache.db')); + +=head1 DESCRIPTION + +POE::Component::IRC::Plugin::Seen is a PoCo-IRC plugin that remembers what each person around it did last. + +When somebody sends him a private message of the form 'seen NICKNAME' or somebody says 'botnick: seen NICKNAME' in a channel with the bot, the plugin answers with the last action NICKNAME did. + +=head1 METHODS + +=over + +=item B([I => value]) + +Creates a new plugin object suitable for L's C method. + +Takes one optional argument, C, the name of the file to store the plugin's state in. If C or not given, it keeps the state in memory. + +=back + +=head1 SEE ALSO + +L + +=head1 AUTHOR + +Marius Gavrilescu C<< >> + +=head1 COPYRIGHT AND LICENSE + +Copyright (C) 2013 by Marius Gavrilescu + +This library is free software; you can redistribute it and/or modify +it under the same terms as Perl itself, either Perl version 5.14.2 or, +at your option, any later version of Perl 5 you may have available. + + +=cut diff --git a/t/POE-Component-IRC-Plugin-Seen.t b/t/POE-Component-IRC-Plugin-Seen.t new file mode 100644 index 0000000..0a0d925 --- /dev/null +++ b/t/POE-Component-IRC-Plugin-Seen.t @@ -0,0 +1,45 @@ +use v5.14; +use strict; +use warnings; + +use Test::More tests => 8; +use Test::MockObject; + +BEGIN { *CORE::GLOBAL::localtime = sub { 'now' } } + +BEGIN { use_ok('POE::Component::IRC::Plugin::Seen') }; + +# Variable setup +my $last_msg; + +my $mockirc = Test::MockObject->new; +$mockirc->mock(yield => sub { $last_msg = $_[3] if $_[1] eq 'privmsg'})->set_always(nick_name => 'bot'); + +my $self = POE::Component::IRC::Plugin::Seen->new; +my $channels = [ '#chan' ]; +my $rmgv = \'mgv!marius@ieval.ro'; + +# Sub setup +sub runtest{ + my ($message, $expect, $comment) = @_; + undef $last_msg; + $self->S_public($mockirc, $rmgv, \$channels, \$message); + is($last_msg, $expect, $comment) +} + +runtest 'something', undef, 'initialize'; +runtest 'bot: seen mgv', 'I last saw mgv now on #chan saying something', 'public'; + +$self->S_ctcp_action($mockirc, $rmgv, \$channels, \'sleeping'); +runtest 'bot: seen mgv', 'I last saw mgv now on #chan doing: * sleeping', 'ctcp_action'; + +$self->S_join($mockirc, $rmgv, \'#chan'); +runtest 'bot: seen mgv', 'I last saw mgv now joining #chan', 'join'; + +$self->S_part($mockirc, $rmgv, \'#chan', \''); +runtest 'bot: seen mgv', 'I last saw mgv now parting #chan', 'part without message'; + +$self->S_part($mockirc, $rmgv, \'#chan', \'buh-bye'); +runtest 'bot: seen mgv', "I last saw mgv now parting #chan with message 'buh-bye'", 'part with message'; + +runtest 'bot: seen asd', "I haven't seen asd", "haven't seen"; -- 2.39.2