The Perl Toolchain Summit needs more sponsors. If your company depends on Perl, please support this very important event.

NAME

Authen::HTTP::Signature - Sign and validate HTTP headers

VERSION

Version 0.03

SYNOPSIS

Create signatures:

    use 5.010;
    use Authen::HTTP::Signature;
    use File::Slurp qw(read_file);
    use HTTP::Request::Common;

    my $key_string = read_file("/my/priv/key.pem") or die $!;

    my $signer = Authen::HTTP::Signature->new(
        key => $key_string,
        key_id => 'Test',
    );

    my $req = POST('http://example.com/foo?param=value&pet=dog',
            Content_Type => 'application/json',
            Content_MD5 => 'Sd/dVLAcvNLSq16eXua5uQ==',
            Content_Length => 18,
            Content => '{"hello": "world"}'
    );

    my $signed_req = $signer->sign($req);

    # adds then signs the 'Date' header with private key using
    # RSA-SHA256, then adds 'Authorization' header to
    # $req

Validate signatures:

    use 5.010;
    use Authen::HTTP::Signature::Parser;
    use HTTP::Request::Common;
    use File::Slurp qw(read_file);
    use Try::Tiny;

    my $req = POST('http://example.com/foo?param=value&pet=dog',
            Content_Type => 'application/json',
            Content_MD5 => 'Sd/dVLAcvNLSq16eXua5uQ==',
            Content_Length => 18,
            Date => 'Thu, 05 Jan 2012 21:31:40 GMT',
            Authorization => q{Signature keyId="Test",algorithm="rsa-sha256",signature="ATp0r26dbMIxOopqw0OfABDT7CKMIoENumuruOtarj8n/97Q3htHFYpH8yOSQk3Z5zh8UxUym6FYTb5+A0Nz3NRsXJibnYi7brE/4tx5But9kkFGzG+xpUmimN4c3TMN7OFH//+r8hBf7BT9/GmHDUVZT2JzWGLZES2xDOUuMtA="},
            Content => '{"hello": "world"}'
    );

    my $p;
    try {
        $p = Authen::HTTP::Signature::Parser->new($req)->parse();
    }
    catch {
        die "Parse failed: $_\n";
    };

    my $key_string = read_file("/my/pub/key.pem") or die $!;
    $p->key( $key_string );

    if ( $p->verify() ) {
        say "Request is valid!"
    }
    else {
        say "Request isn't valid";
    };

PURPOSE

This is an implementation of the IETF HTTP Signatures specification authentication scheme. The idea is to authenticate connections (over HTTPS ideally) using either an RSA keypair or a symmetric key by signing a set of header values.

If you wish to use SSH keys for validation as in Joyent's proposal, check out Convert::SSH2.

ATTRIBUTES

These are Perlish mutators; give an argument to set a value or no argument to get the current value.

algorithm

The algorithm to use for signing. Read-only.

One of:

  • rsa-sha1

  • rsa-sha256 (default)

  • rsa-sha512

  • hmac-sha1

  • hmac-sha256

  • hmac-sha512

headers

The list of headers to be signed (or already signed.) Defaults to the 'Date' header. The order of the headers in this list will be used to build the order of the text in the signing string.

This attribute can have a psuedo-value. It is:

  • request-line

    Use the method, text of the path and query from the request, and the protocol version signature (i.e., /foo?param=value&pet=dog HTTP/1.1) as part of the signing string.

  • (request-target)

    Use the method, text of the path and query from the request (i.e., get /foo?param=value&pet=dog) as part of the signing string.

signing_string

The string used to compute the signature digest. It contents are derived from the values of the headers array.

signature

Contains the digital signature authorization data.

extensions

There are currently no extentions implemented by this library, but the library will append extension information to the generated header data if this attribute has a value.

key

The key to use for cryptographic operations. The key type may have specific meaning based on the algorithm used. RSA requires private keys for signing and the corresponding public key for validation. See the specific implementation module for more details about what this value should be.

key_id

Required.

A means to identify the key being used to both sender and receiver. This can be any token which makes sense to the sender and receiver. The exact specification of a token and any necessary key management are outside the scope of this library.

request

Holds the request to be parsed. Should be some kind of 'Request' object with an interface to get/set headers.

get_header

Expects a CODE reference.

This callback represents the method to get header values from the object in the request attribute.

The request will be the first parameter, and name of the header to fetch a value will be provided as the second parameter to the callback.

NOTE: The callback should be prepared to handle a "pseudo-header" of request-line which is the path and query portions of the request's URI and HTTP version string. (For more information see the HTTP signature specification.)

set_header

Expects a CODE reference.

This callback represents the way to set header values on the object in the request attribute.

The request will be the first parameter. The name of the header and its value will be the second and third parameters.

Returns the request object.

authorizaton_string

The text to identify the HTTP signature authorization scheme. Currently defined as the string literal 'Signature'. Read-only.

METHODS

Errors are generally fatal. Use Try::Tiny for more graceful error handling.

sign()

This method takes signs the values of the specified headers using algorithm and key.

By default, it uses request as its input. You may optionally pass a request object and it will use that instead. By default, it uses key. You may optionally pass key material and it will use that instead.

It will add a Date header to the request if there isn't already one in the request object.

It adds a Authorization header with the appropriate signature data.

The return value is a signed request object.

verify()

This method verifies that a signature on a request is valid.

By default it uses key. You may optionally pass in key material and it will use that instead.

Returns a boolean.

AUTHOR

Mark Allen, <mrallen1 at yahoo.com>

BUGS

Please report any bugs or feature requests to bug-authen-http-signature at rt.cpan.org, or through the web interface at http://rt.cpan.org/NoAuth/ReportBug.html?Queue=Authen-HTTP-Signature. I will be notified, and then you'll automatically be notified of progress on your bug as I make changes.

SUPPORT

You can find documentation for this module with the perldoc command.

    perldoc Authen::HTTP::Signature

You can also look for information at:

SEE ALSO

Authen::HTTP::Signature::Parser, Authen::HTTP::Signature::Method::HMAC, Authen::HTTP::Signature::Method::RSA

Joyent's HTTP Signature specification

LICENSE AND COPYRIGHT

Copyright 2012 Mark Allen.

This program is free software; you can redistribute it and/or modify it under the terms of either: the GNU General Public License as published by the Free Software Foundation; or the Artistic License.

See http://dev.perl.org/licenses/ for more information.