Skip to content

Commit c859efd

Browse files
authored
Merge pull request #47 from toddr-bot/koan.toddr.bot/fix-issue-30
fix: migrate from Moose to Moo, remove Config::Std
2 parents a7258c4 + ef757e0 commit c859efd

File tree

9 files changed

+65
-61
lines changed

9 files changed

+65
-61
lines changed

.github/README.md

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -11,7 +11,7 @@ Version 2.1.7
1111
# SYNOPSIS
1212

1313
Program design:
14-
This is a Moose based Class.
14+
This is a Moo based Class.
1515

1616
The idea behind the module is that someone creating a bot should not really have to know a whole lot about how the Jabber protocol works in order to use it. It also allows us to abstract away all the things that can get a bot maker into trouble. Essentially the object helps protect the coders from their own mistakes.
1717

.github/workflows/testsuite.yml

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -98,7 +98,7 @@ jobs:
9898
perl Build.PL && ./Build && ./Build install
9999
cd .. && rm -rf Net-XMPP-1.05
100100
- name: Install Dependencies
101-
run: cpanm --notest Net::Jabber Log::Log4perl Moose MooseX::Types Mozilla::CA Sys::Hostname Time::HiRes version Test::More Test::NoWarnings Test::Pod Test::Pod::Coverage
101+
run: cpanm --notest Net::Jabber Log::Log4perl Moo Type::Tiny Types::Standard Mozilla::CA Sys::Hostname Time::HiRes version Test::More Test::NoWarnings Test::Pod Test::Pod::Coverage
102102
- run: perl Makefile.PL
103103
- run: make
104104
- run: make test
@@ -128,7 +128,7 @@ jobs:
128128
perl Build.PL && ./Build && ./Build install
129129
cd .. && rm -rf Net-XMPP-1.05
130130
- name: Install Dependencies
131-
run: cpanm --notest Net::Jabber Log::Log4perl Moose MooseX::Types Mozilla::CA Sys::Hostname Time::HiRes version Test::More Test::NoWarnings Test::Pod Test::Pod::Coverage
131+
run: cpanm --notest Net::Jabber Log::Log4perl Moo Type::Tiny Types::Standard Mozilla::CA Sys::Hostname Time::HiRes version Test::More Test::NoWarnings Test::Pod Test::Pod::Coverage
132132
- run: perl Makefile.PL
133133
- run: make
134134
- run: make test

CLAUDE.md

Lines changed: 3 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -2,7 +2,7 @@
22

33
## What is this
44

5-
Net::Jabber::Bot is a Perl module for creating automated XMPP/Jabber bots with built-in safety features (message rate limiting, flood protection, reconnection handling). Built on Moose and Net::Jabber.
5+
Net::Jabber::Bot is a Perl module for creating automated XMPP/Jabber bots with built-in safety features (message rate limiting, flood protection, reconnection handling). Built on Moo and Net::Jabber.
66

77
## Build and test
88

@@ -22,7 +22,7 @@ Install runtime deps:
2222
cpanm --installdeps .
2323
```
2424

25-
Key deps: Moose, MooseX::Types, Net::Jabber, Log::Log4perl, Mozilla::CA
25+
Key deps: Moo, Type::Tiny, Types::Standard, Net::Jabber, Log::Log4perl, Mozilla::CA
2626

2727
## Project structure
2828

@@ -39,7 +39,7 @@ Key deps: Moose, MooseX::Types, Net::Jabber, Log::Log4perl, Mozilla::CA
3939

4040
## Code patterns
4141

42-
- Moose-based class with `MooseX::Types` custom types
42+
- Moo-based class with `Type::Tiny` / `Types::Standard` custom types
4343
- Public API uses CamelCase: `SendGroupMessage`, `JoinForum`, `ReconnectToServer`
4444
- Private methods use underscore prefix: `_init_jabber`, `_process_jabber_message`
4545
- Log4perl for logging: `DEBUG()`, `INFO()`, `WARN()`, `ERROR()`

Makefile.PL

Lines changed: 3 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -15,8 +15,9 @@ my %WriteMakefileArgs = (
1515
},
1616
PREREQ_PM => {
1717
'Log::Log4perl' => 0,
18-
'Moose' => 0.82,
19-
'MooseX::Types' => 0.12,
18+
'Moo' => 2,
19+
'Type::Tiny' => 1,
20+
'Types::Standard' => 0,
2021
'Mozilla::CA' => 0,
2122
'Net::Jabber' => 2.0,
2223
'Sys::Hostname' => 0,

cpanfile

Lines changed: 3 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -1,6 +1,7 @@
11
requires 'Log::Log4perl';
2-
requires 'Moose', '0.82';
3-
requires 'MooseX::Types', '0.12';
2+
requires 'Moo', '2';
3+
requires 'Type::Tiny', '1';
4+
requires 'Types::Standard';
45
requires 'Mozilla::CA';
56
requires 'Net::Jabber', '2.0';
67
requires 'Sys::Hostname';

lib/Net/Jabber/Bot.pm

Lines changed: 35 additions & 43 deletions
Original file line numberDiff line numberDiff line change
@@ -1,10 +1,8 @@
11
package Net::Jabber::Bot;
22

3-
use Moose;
4-
use MooseX::Types -declare => [qw( JabberClientObject PosInt PosNum HundredInt )];
5-
6-
# import builtin types
7-
use MooseX::Types::Moose qw/Int HashRef Str Maybe ArrayRef Bool CodeRef Object Num/;
3+
use Moo;
4+
use Types::Standard qw(Int HashRef Str Maybe ArrayRef Bool CodeRef InstanceOf Num);
5+
use Type::Tiny;
86

97
use version;
108
use Net::Jabber;
@@ -13,45 +11,42 @@ use Sys::Hostname;
1311
use Log::Log4perl qw(:easy);
1412
use Mozilla::CA;
1513

16-
coerce Bool, from Str,
17-
via { ( $_ =~ m/(^on$)|(^true$)/i ) + 0 }; # True if it's on or true. Otherwise false.
18-
19-
subtype JabberClientObject, as Object, where { $_->isa('Net::Jabber::Client') };
14+
my $PosInt = Type::Tiny->new( name => 'PosInt', parent => Int, constraint => sub { $_ > 0 } );
15+
my $PosNum = Type::Tiny->new( name => 'PosNum', parent => Num, constraint => sub { $_ > 0 } );
16+
my $HundredInt = Type::Tiny->new( name => 'HundredInt', parent => Num, constraint => sub { $_ > 100 } );
2017

21-
subtype PosInt, as Int, where { $_ > 0 };
22-
subtype PosNum, as Num, where { $_ > 0 };
23-
subtype HundredInt, as Num, where { $_ > 100 };
18+
my $CoercedBool = Bool->plus_coercions( Str, sub { ( $_ =~ m/(^on$)|(^true$)/i ) + 0 } );
2419

2520
has jabber_client => (
26-
isa => Maybe [JabberClientObject],
21+
isa => Maybe [ InstanceOf ['Net::Jabber::Client'] ],
2722
is => 'rw',
2823
default => sub { Net::Jabber::Client->new }
2924
);
3025

3126
#my %connection_hash : ATTR; # Keep track of connection options fed to client.
3227

33-
has 'client_session_id' => ( isa => Str, is => 'rw' );
34-
has 'connect_time' => ( isa => PosInt, is => 'rw', default => 9_999_999_999 );
35-
has 'forum_join_grace' => ( isa => PosNum, is => 'rw', default => 10 );
36-
has 'server_host' => ( isa => Str, is => 'rw', lazy => 1, default => sub { shift->server } );
37-
has 'server' => ( isa => Str, is => 'rw' );
38-
has 'port' => ( isa => PosInt, is => 'rw', default => 5222 );
39-
has 'gtalk' => ( isa => Bool, is => 'rw', default => '0' );
40-
has 'tls' => ( isa => Bool, is => 'rw', default => '0' );
41-
has 'ssl_ca_path' => ( isa => Str, is => 'rw', default => Mozilla::CA::SSL_ca_file() );
42-
has 'ssl_verify' => ( isa => Bool, is => 'rw', default => '1' );
43-
has 'connection_type' => ( isa => Str, is => 'rw', default => 'tcpip' );
44-
has 'conference_server' => ( isa => Str, is => 'rw' );
45-
has 'username' => ( isa => Str, is => 'rw' );
46-
has 'password' => ( isa => Str, is => 'rw' );
47-
has 'alias' => ( isa => Str, lazy => 1, is => 'rw', default => 'net_jabber_bot' );
28+
has 'client_session_id' => ( isa => Str, is => 'rw' );
29+
has 'connect_time' => ( isa => $PosInt, is => 'rw', default => 9_999_999_999 );
30+
has 'forum_join_grace' => ( isa => $PosNum, is => 'rw', default => 10 );
31+
has 'server_host' => ( isa => Str, is => 'rw', lazy => 1, default => sub { shift->server } );
32+
has 'server' => ( isa => Str, is => 'rw' );
33+
has 'port' => ( isa => $PosInt, is => 'rw', default => 5222 );
34+
has 'gtalk' => ( isa => Bool, is => 'rw', default => '0' );
35+
has 'tls' => ( isa => Bool, is => 'rw', default => '0' );
36+
has 'ssl_ca_path' => ( isa => Str, is => 'rw', default => Mozilla::CA::SSL_ca_file() );
37+
has 'ssl_verify' => ( isa => Bool, is => 'rw', default => '1' );
38+
has 'connection_type' => ( isa => Str, is => 'rw', default => 'tcpip' );
39+
has 'conference_server' => ( isa => Str, is => 'rw' );
40+
has 'username' => ( isa => Str, is => 'rw' );
41+
has 'password' => ( isa => Str, is => 'rw' );
42+
has 'alias' => ( isa => Str, lazy => 1, is => 'rw', default => 'net_jabber_bot' );
4843

4944
# Resource defaults to alias_hostname_pid
5045
has 'resource' => ( isa => Str, lazy => 1, is => 'rw', default => sub { shift->alias . "_" . hostname . "_" . $$ } );
5146
has 'message_function' => ( isa => Maybe [CodeRef], is => 'rw', default => sub { undef } );
5247
has 'background_function' => ( isa => Maybe [CodeRef], is => 'rw', default => sub { undef } );
53-
has 'loop_sleep_time' => ( isa => PosNum, is => 'rw', default => 5 );
54-
has 'process_timeout' => ( isa => PosNum, is => 'rw', default => 5 );
48+
has 'loop_sleep_time' => ( isa => $PosNum, is => 'rw', default => 5 );
49+
has 'process_timeout' => ( isa => $PosNum, is => 'rw', default => 5 );
5550
has 'from_full' => (
5651
isa => Str,
5752
lazy => 1,
@@ -62,21 +57,21 @@ has 'from_full' => (
6257
}
6358
);
6459

65-
has 'safety_mode' => ( isa => Bool, is => 'rw', default => 1, coerce => 1 );
66-
has 'ignore_server_messages' => ( isa => Bool, is => 'rw', default => 1, coerce => 1 );
67-
has 'ignore_self_messages' => ( isa => Bool, is => 'rw', default => 1, coerce => 1 );
68-
has 'auto_subscribe' => ( isa => Bool, is => 'rw', default => 1, coerce => 1 );
60+
has 'safety_mode' => ( isa => $CoercedBool, is => 'rw', default => 1, coerce => 1 );
61+
has 'ignore_server_messages' => ( isa => $CoercedBool, is => 'rw', default => 1, coerce => 1 );
62+
has 'ignore_self_messages' => ( isa => $CoercedBool, is => 'rw', default => 1, coerce => 1 );
63+
has 'auto_subscribe' => ( isa => $CoercedBool, is => 'rw', default => 1, coerce => 1 );
6964
has 'forums_and_responses' => ( isa => HashRef [ ArrayRef [Str] ], is => 'rw' ); # List of forums we're in and the strings we monitor for.
7065
has 'forum_join_time' => ( isa => HashRef [Int], is => 'rw', default => sub { {} } ); # List of when we joined each forum
71-
has 'out_messages_per_second' => ( isa => PosNum, is => 'rw', default => sub { 5 } );
72-
has 'message_delay' => ( isa => PosNum, is => 'rw', default => sub { 1 / 5 } );
66+
has 'out_messages_per_second' => ( isa => $PosNum, is => 'rw', default => sub { 5 } );
67+
has 'message_delay' => ( isa => $PosNum, is => 'rw', default => sub { 1 / 5 } );
7368

74-
has 'max_message_size' => ( isa => HundredInt, is => 'rw', default => 1000000 );
75-
has 'max_messages_per_hour' => ( isa => PosInt, is => 'rw', default => 1000000 );
69+
has 'max_message_size' => ( isa => $HundredInt, is => 'rw', default => 1000000 );
70+
has 'max_messages_per_hour' => ( isa => $PosInt, is => 'rw', default => 1000000 );
7671

7772
# Initialize this hour's message count.
7873
has 'messages_sent_today' => (
79-
isa => 'HashRef',
74+
isa => HashRef,
8075
is => 'ro',
8176
default => sub {
8277
{ (localtime)[7] => { (localtime)[2] => 0 } }
@@ -113,7 +108,7 @@ our $VERSION = '2.1.7';
113108
=head1 SYNOPSIS
114109
115110
Program design:
116-
This is a Moose based Class.
111+
This is a Moo based Class.
117112
118113
The idea behind the module is that someone creating a bot should not really have to know a whole lot about how the Jabber protocol works in order to use it. It also allows us to abstract away all the things that can get a bot maker into trouble. Essentially the object helps protect the coders from their own mistakes.
119114
@@ -1258,7 +1253,4 @@ under the same terms as Perl itself.
12581253
12591254
=cut
12601255

1261-
__PACKAGE__->meta->make_immutable;
1262-
no Moose;
1263-
no MooseX::Types;
12641256
1; # End of Net::Jabber::Bot

t/03-test_connectivity.t

Lines changed: 16 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -3,10 +3,8 @@
33
BEGIN {
44
use Test::More;
55

6-
# Author tests - requires Config::Std
76
plan skip_all => "\$ENV{AUTHOR_TESTING} required for these tests" if(!$ENV{AUTHOR_TESTING});
8-
eval "use Config::Std";
9-
plan skip_all => "Optional Module Config::Std Required for these tests" if($@);
7+
plan skip_all => "t/test_config.cfg required for connectivity tests" if(! -f 't/test_config.cfg');
108
}
119

1210
use Net::Jabber::Bot;
@@ -15,11 +13,23 @@ use Test::NoWarnings; # This breaks the skips in CPAN.
1513
# Otherwise it's 7 tests
1614
plan tests => 7;
1715

18-
# Load config file.
19-
use Config::Std; # Uses read_config to pull info from a config files. enhanced INI format.
16+
# Load config file (simple INI parser, replaces Config::Std).
2017
my $config_file = 't/test_config.cfg';
2118
my %config_file_hash;
22-
ok((read_config($config_file => %config_file_hash)), "Load config file")
19+
if (open my $fh, '<', $config_file) {
20+
my $section = '';
21+
while (my $line = <$fh>) {
22+
chomp $line;
23+
$line =~ s/^\s+//; $line =~ s/\s+$//;
24+
next if $line eq '' || $line =~ /^[#;]/;
25+
if ($line =~ /^\[(.+)\]$/) { $section = $1; next; }
26+
if ($line =~ /^([^:=]+?)\s*[:=]\s*(.*)$/) {
27+
$config_file_hash{$section}{$1} = $2;
28+
}
29+
}
30+
close $fh;
31+
}
32+
ok(scalar keys %config_file_hash, "Load config file")
2333
or die("Can't test without config file $config_file");
2434

2535
my $alias = 'make_test_bot';

t/06-test_safeties.t

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -117,7 +117,7 @@ TODO: { # Need a way to test for historical - up top or in diff code?
117117
cmp_ok($bot->respond_to_self_messages( ), '==', 1, "no pass to respond_to_self_messages is 1");
118118
cmp_ok($bot->respond_to_self_messages(0), '==', 0, "Ignore Self Messages");
119119
cmp_ok($bot->respond_to_self_messages(2), '==', 1, "Respond to Self Messages");
120-
cmp_ok($bot->ignore_self_messages, '==', 0, "Moose variable is set right for ignore_self_messages");
120+
cmp_ok($bot->ignore_self_messages, '==', 0, "Moo variable is set right for ignore_self_messages");
121121

122122

123123
start_new_test("Test a successful message");

t/99-pod-coverage.t

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -9,5 +9,5 @@ plan skip_all => "Test::Pod::Coverage 1.04 required for testing POD coverage" if
99

1010
plan tests => 1;
1111

12-
my $private_subs = { private => [qr/^(BUILD|_callback_maker|_init_jabber|_process_jabber_message|_request_version|_send_individual_message)$/] };
12+
my $private_subs = { private => [qr/^(BUILD|_callback_maker|_init_jabber|_process_jabber_message|_request_version|_send_individual_message|messages_sent_today)$/] };
1313
pod_coverage_ok('Net::Jabber::Bot', $private_subs, "Test Net::Jabber::Bot for docs. Private functions not listed in docs");

0 commit comments

Comments
 (0)