package WWW::Anonymouse; use strict; use warnings; use LWP::UserAgent; use URI; use Carp (); our $VERSION = '0.04'; use constant DEBUG => $ENV{ WWW_ANONYMOUSE_DEBUG } || 0; use constant MAX_BYTES => 3072; sub new { my ($class, %params) = @_; if ( $class eq __PACKAGE__ ) { Carp::croak __PACKAGE__, ' is a virtual class; use the Email or News class'; } unless ( ref $params{ua} and $params{ua}->isa( q(LWP::UserAgent) ) ) { $params{ua} = LWP::UserAgent->new( agent => __PACKAGE__.'/'.$VERSION ); } return bless \%params, $class; } sub error { return $_[0]->{error}; } sub _ua_content_cb { my ($data, $res, $proto) = @_; $res->add_content(\$data); # Abort the request if enough content is received to parse for status. die if length $res->content > MAX_BYTES; } sub send { my ($self, %params) = @_; my %fields; unless ( $fields{qw( to )} = $params{qw( to )} ) { $self->{error} = qq(Missing field "to"); return; } for my $field ( qw( subject text ) ) { $fields{$field} = $params{$field} || ''; } my $res = $self->{ua}->post( $self->_url, \%fields, ':read_size_hint' => MAX_BYTES, ':content_cb' => \&_ua_content_cb, ); unless ( $res->is_success ) { $self->{error} = $res->status_line; return; } # TODO: consider using HTML::TreeBuilder::XPath $self->{error} = 'Unknown error'; my $cref = $res->content_ref; if ( $$cref !~ /(?:Mixmaster-)?Error - ([^>]+?)\!?{error} = $1; } elsif ( $$cref =~ /\G>(?:Email|Posting) has been sent anonymously/ ) { $self->{error} = undef; return 1; } return; } BEGIN { package WWW::Anonymouse::Email; use base qw( WWW::Anonymouse ); sub _url { 'http://anonymouse.org/cgi-bin/anon-email.cgi' } sub _referer { 'http://anonymouse.org/anonemail.html' } } BEGIN { package WWW::Anonymouse::News; use base qw( WWW::Anonymouse ); sub _url { 'http://anonymouse.org/cgi-bin/anon-news.cgi' } sub _referer { 'http://anonymouse.org/anonnews.html' } } 1; __END__ =head1 NAME WWW::Anonymouse - interface to Anonymouse.org Email and News posting =head1 SYNOPSIS use WWW::Anonymouse; my $an = WWW::Anonymouse::Email->new; $an->send( to=>'bubba@example.com', subject=>'test', text=>'test' ); my $an = WWW::Anonymouse::News->new; $an->send( to=>'alt.test', subject=>'test', text=>'test' ); =head1 DESCRIPTION The C module provides an interface to the Anonymouse.org anonymous email and news posting. =head1 METHODS =over =item $an = WWW::Anonymouse::Email->B =item $an = WWW::Anonymouse::Email->B( ua => $ua ) =item $an = WWW::Anonymouse::News->B =item $an = WWW::Anonymouse::News->B( ua => $ua ) Creates a new Email or News object. The constructor accepts an optional LWP::UserAgent derived object. =item $ret = $an->B( to => $to, subject => $subject, text => $text ) Sends a message to the given email address(es) or newsgroup(s). Returns true on success. =item $error = $an->B Returns the error string, if present. =back =head1 NOTES Anonymouse has a flood protection limit of about 1 message per minute. If you need to post more frequently, you can use http proxies or cgi proxies- but don't abuse the service. =head1 SEE ALSO L L =head1 REQUESTS AND BUGS Please report any bugs or feature requests to L. I will be notified, and then you'll automatically be notified of progress on your bug as I make changes. =head1 SUPPORT You can find documentation for this module with the perldoc command. perldoc WWW::Anonymouse You can also look for information at: =over =item * AnnoCPAN: Annotated CPAN documentation L =item * CPAN Ratings L =item * RT: CPAN's request tracker L =item * Search CPAN L =back =head1 COPYRIGHT AND LICENSE Copyright (C) 2007 gray , all rights reserved. This library is free software; you can redistribute it and/or modify it under the same terms as Perl itself. =head1 AUTHOR gray, =cut