The London Perl and Raku Workshop takes place on 26th Oct 2024. If your company depends on Perl, please consider sponsoring and/or attending.


RAPNAP::client - perform a check against the RAPNAP database


  use RAPNAP::client; # use default key, limited and accounted by IP
  # use RAPNAP::client 'AssignedKey'; # contact for a key
  ... # parse the headers of an e-mail or SMTP data block
  $RAPNAP_RESULT = rapnap_check($return_address,$peer_network_address,
  if ($RAPNAP_RESULT =~ /> GOOD\b/){
        # continue delivering message
        # refuse or defer delivery


RAPNAP::client provides a client for the RAPNAP database, which is a database of valid e-mail senders and the e-mail relays that their e-mail originates from. pursues a vision of e-mail that costs money to send, except for whitelisted correspondents. This client module connects to and offers the RA ("Return Address") and PNA ("Peer Network Address") specified as the first and second arguments to the <Crapnap_check()> function which is exported by this module.

The rapnap_check() function takes two required and three optional arguments:


Return Address (in dotted quad form. ipv6 addresses are not supported yet.)


Peer Network Address


Subject Line -- the subject line of the e-mail we are evaluating


TArget -- to whom the e-mail we are evaluating is addressed


TEmplate -- the message template to use in the confirmation message

and returns the text of the web page. ra and pna are required to get a response. If a dns lookup on pna produces a name that does not map back to the provided address, that is considered an error.

Subject Line and TArget are required to fill in the blanks in the message template, and the rapnap checking routine will not send e-mails unless they are provided.

TEmplate is parameterized so that you can compose your own message template, following the example at and have messages sent to people because they are sending you or yours mail from unlisted sources customized. Information about the source of queries is provided in the e-mail headers, before the template is streamed in.

By default, RAPNAP::client uses a pay2send account key of "ipv4" which allows a limited number of accesses per day from an IP address.

See the web site for information on getting a pay2send RAPNAP client key which will allow more accesses per day.

The rapnap_check function returns the text of the web page, which will begin "error" is something went wrong, and will match

        ($RA2, $dnsname, $PNA2, $result, $count, $more) =
        ($QueryResult = rapnap_check($RA, $PNA)) =~ 
        m/^(\S+) VIA (\S+) \[([\d\.]+)\] -> (UNKNOWN|GOOD|BAD) (\d+)(.*)/s;

otherwise, that is, if the query was syntacticly valid and the network address was not mapped to a name that does not map back to the same address.

There may be additional information after the restatement of the query, the result, and the count of queries so far today, for the provided key, or $QueryResult might begin /^error / in which case something went wrong, such as the RA containing a percent sign, or being over the limit of queries.

When a sender has agreed to pay to send e-mail, the $more field will contain information about this, in the form of text matching

        ($USD_amount) = $more =~ /WILL_PAY (\d*\.?\d*) USD/;

At this time there is no concrete plan for the pay2send infrastructure to work with currencies other than the United States Dollar.


the rapnap_check() function, described above, is exported.


The to-do list includes:


keep a cache of results, so we don't make redundant queries.


support http/1.1 keepalive for use with RAPNAP clients that are going to last longer than evaluating one message

http/1.1 cacheing support

use If-Modified-Since and a local cache of results. Right now the RAPNAP server doesn't issue etags, so this wouldn't help. Caching the results from a particular RAPNAP for a day or so is a best practice, at this time.

DNS-based RAPNAP checking

first we need to serve the RAPNAP database via DNS, which we aren't doing yet.



21 March 2003. Written during the U.S. assault on Iraq. Support for HTTP/1.1 POST request with default key.


15 April 2003. Documented optional parameters, WILL PAY syntax. Iraq is secure.


Copyright (C) 2003 David Nicol / / Tipjar LLC (I have a patent pending on using RAPNAP pairs for identity verification stronger than available in SMTP return address claims, which are trivially forged.)

this module is released GPL/AL: the same terms as Perl


4 POD Errors

The following errors were encountered while parsing the POD:

Around line 186:

'=item' outside of any '=over'

Around line 209:

You forgot a '=back' before '=head1'

Around line 211:

'=item' outside of any '=over'

Around line 221:

You forgot a '=back' before '=head1'