192 lines
4.7 KiB
192 lines
4.7 KiB
package NGCP::TestFramework::Client;
|
|
|
|
use strict;
|
|
use warnings;
|
|
use Data::Dumper;
|
|
use Digest::MD5 qw/md5_hex/;
|
|
use IO::Uncompress::Unzip;
|
|
use LWP::UserAgent;
|
|
use Moose;
|
|
use Time::HiRes qw/gettimeofday tv_interval/;
|
|
|
|
has 'username' => (
|
|
isa => 'Str',
|
|
is => 'ro',
|
|
default => sub {
|
|
$ENV{API_USER} // 'administrator';
|
|
}
|
|
);
|
|
|
|
has 'password' => (
|
|
isa => 'Str',
|
|
is => 'ro',
|
|
default => sub {
|
|
$ENV{API_PASS} // 'administrator';
|
|
}
|
|
);
|
|
|
|
has 'role' => (
|
|
isa => 'Str',
|
|
is => 'ro',
|
|
default => 'admin',
|
|
);
|
|
|
|
has 'uri' => (
|
|
isa => 'Str',
|
|
is => 'ro',
|
|
default => sub { $ENV{CATALYST_SERVER}; },
|
|
);
|
|
|
|
has 'sub_uri' => (
|
|
isa => 'Str',
|
|
is => 'ro',
|
|
default => sub { $ENV{CATALYST_SERVER_SUB}; },
|
|
);
|
|
|
|
has '_uri' => (
|
|
isa => 'Maybe[Str]',
|
|
is => 'rw',
|
|
);
|
|
|
|
has 'verify_ssl' => (
|
|
isa => 'Int',
|
|
is => 'ro',
|
|
default => 0,
|
|
);
|
|
|
|
has 'log_debug' => (
|
|
isa => 'Bool',
|
|
is => 'rw',
|
|
default => 0,
|
|
);
|
|
|
|
has '_crt_path' => (
|
|
is => 'ro',
|
|
isa => 'Str',
|
|
lazy => 1,
|
|
default => sub {
|
|
my ($self) = @_;
|
|
return '/tmp/' . md5_hex($self->username) . ".crt";
|
|
}
|
|
);
|
|
|
|
has 'last_rtt' => (
|
|
is => 'rw',
|
|
isa => 'Num',
|
|
default => 0,
|
|
);
|
|
|
|
has '_ua' => (
|
|
isa => 'LWP::UserAgent',
|
|
is => 'ro',
|
|
lazy => 1,
|
|
builder => '_build_ua'
|
|
);
|
|
|
|
sub _build_ua {
|
|
my $self = shift;
|
|
|
|
my $ua = LWP::UserAgent->new(keep_alive => 1);
|
|
my $uri;
|
|
if($self->role eq "admin" || $self->role eq "reseller") {
|
|
$uri = $self->uri;
|
|
} else {
|
|
$uri = $self->sub_uri;
|
|
}
|
|
$self->_uri($uri);
|
|
$self->debug("client using uri $uri\n");
|
|
$uri =~ s/^https?:\/\///;
|
|
$self->debug("client using ip:port $uri\n");
|
|
my $realm;
|
|
if($self->role eq 'admin' || $self->role eq 'reseller') {
|
|
$realm = 'api_admin_http';
|
|
} elsif($self->role eq 'subscriber') {
|
|
$realm = 'api_subscriber_http';
|
|
}
|
|
$self->debug("client using realm $realm with user=" . $self->username . " and pass " . $self->password . "\n");
|
|
$ua->credentials($uri, $realm, $self->username, $self->password);
|
|
unless($self->verify_ssl) {
|
|
$ua->ssl_opts(
|
|
verify_hostname => 0,
|
|
SSL_verify_mode => 0,
|
|
);
|
|
}
|
|
if($self->role eq "admin" || $self->role eq "reseller") {
|
|
unless(-f $self->_crt_path) {
|
|
|
|
# we have to setup a new connection here, because if we're already connected,
|
|
# the connection will be re-used, thus no cert is used
|
|
my $tmpua = LWP::UserAgent->new;
|
|
$tmpua->credentials($uri, $realm, $self->username, $self->password);
|
|
unless($self->verify_ssl) {
|
|
$tmpua->ssl_opts(
|
|
verify_hostname => 0,
|
|
SSL_verify_mode => 0,
|
|
);
|
|
}
|
|
|
|
my $res = $tmpua->post(
|
|
$self->_uri . '/api/admincerts/',
|
|
Content_Type => 'application/json',
|
|
Content => '{}'
|
|
);
|
|
unless($res->is_success) {
|
|
die "Failed to fetch client certificate: " . $res->status_line . "\n";
|
|
}
|
|
my $zip = $res->decoded_content;
|
|
my $z = IO::Uncompress::Unzip->new(\$zip, MultiStream => 0, Append => 1);
|
|
my $data;
|
|
while(!$z->eof() && (my $hdr = $z->getHeaderInfo())) {
|
|
unless($hdr->{Name} =~ /\.pem$/) {
|
|
# wrong file, just read stream, clear buffer and try next
|
|
while($z->read($data) > 0) {}
|
|
$data = undef;
|
|
$z->nextStream();
|
|
next;
|
|
}
|
|
while($z->read($data) > 0) {}
|
|
last;
|
|
}
|
|
$z->close();
|
|
unless($data) {
|
|
die "Failed to find PEM file in client certificate zip file\n";
|
|
}
|
|
open my $fh, ">:raw", $self->_crt_path
|
|
or die "Failed to open " . $self->_crt_path . ": $!\n";
|
|
print $fh $data;
|
|
close $fh;
|
|
}
|
|
$ua->ssl_opts(
|
|
SSL_cert_file => $self->_crt_path,
|
|
SSL_key_file => $self->_crt_path,
|
|
);
|
|
}
|
|
return $ua;
|
|
}
|
|
|
|
|
|
sub perform_request {
|
|
my ($self, $req) = @_;
|
|
my $t0 = [gettimeofday];
|
|
$self->debug("content of " . $req->method . " request to " . $req->uri . ":\n");
|
|
$self->debug($req->content || "<empty request>");
|
|
$self->debug("\n");
|
|
my $res = $self->_ua->request($req);
|
|
my $rtt = tv_interval($t0);
|
|
$self->last_rtt($rtt);
|
|
$self->debug("content of response:\n");
|
|
$self->debug($res->decoded_content || "<empty response>");
|
|
$self->debug("\n");
|
|
return $res;
|
|
}
|
|
|
|
sub debug {
|
|
my ($self, $msg) = @_;
|
|
if($self->log_debug) {
|
|
print $msg;
|
|
}
|
|
}
|
|
|
|
1;
|
|
|