需求:有些已经实现好的Restful API,通过调用Restful API,取出Restful API的返回值中部分key的值。
1)Rest中,每个对象都是1个URL;
这里需要了解perl发送request,以及怎么处理response.
http://www.redmine.org/projects/redmine/wiki/Rest_api_with_perl
http://search.cpan.org/~ether/libwww-perl-6.15/lib/LWP/UserAgent.pm
2)Restful API的返回值是json格式的,也就是python中的嵌套字典
这里需要学习json的知识
http://search.cpan.org/~makamaka/JSON-2.90/lib/JSON.pm
3)产物作为类提供
需要了解面向对象,除此以外还需要了解perl的哈希,数组,循环等基础知识。
http://www.runoob.com/perl/perl-tutorial.html
一、安装perl IDE
有很多,菜鸟教程也有推荐。这里安装的是Padre
windows PC上装perl IDE:http://padre.perlide.org/
二、练习
就是按照菜鸟教程练习0.5天
三、就是根据需求写脚本
每个URL返回的数据结构如下:
构造函数和一些共通的变量
our $web_base_url = ""; our %web_base_url = (); $web_base_url{testBase} = "this is for URL"; our $ENODEB = CONSTANT VALUE our $CABINET = CONSTANT VALUE our $TELNET = CONSTANT VALUE our $SWITCH = CONSTANT VALUE our $MDU = CONSTANT VALUE our $SYNCHRONIZATION = CONSTANT VALUE our $SOURCE = CONSTANT VALUE ############################################################################## # CONSTRUCTOR # new ( <testplanName> ) # This is the cunstructor for this class ############################################################################## sub new { my $class = shift; my (%params) = @_; my $self = { _baseUrl => $web_base_url{testBase}, _tpname => $params{tpname} }; $self->{URL} = $self->{_baseUrl}.=$self->{_tpname}; bless ($self, $class); $self->_setCisAttributes(); $self->{class} = $class; return $self; }
1.发送get请求,获得responseContent
sub _getResponseContent{ my( $self,$URL) = @_; my $ua = LWP::UserAgent->new( protocols_allowed => [ 'http', 'https' ], timeout => 30, ssl_opts => { verify_hostname => 0 } ); my $retval = {}; my $json = JSON->new->utf8; my $response = $ua->get($URL); if ($response->is_error){ print "Failed to get data by $self->{URL}\n"; die $response->message; } my $content = $response->content; $retval = $json->decode($content); return $retval; }
2.分解每个大的item值
sub _setCisAttributes{ my($self) = @_; $self->{testPlan} = $self->_getResponseContent($self->{URL})->{items}; foreach ( @{ $self->{testPlan} }){ die "Not find key cfItem_type in element $->{'cfItem_type'} $self->{URL}" unless $_->{'cfItem_type'}; if ($_->{'cfItem_type'} =~ /$ENODEB/){ $self->{testRbsHash} = $_; } if ($_->{'cfItem_type'} =~ /$CABINET/){ $self->{testCabinetHash} = $_; } if ($_->{'cfItem_type'} =~ /$TELNET/ and $_->{'cfItem_type'} =~ /$SWITCH/){ $self->{testSwitchHash} = $_; } if ($_->{'cfItem_type'} =~ /$MDU/ and $_->{params}->{Master}->{value} =~ /true/){ $self->{testMduHash} = $_; my $test = scalar($_->{params}->{Master}->{value}); } if ($_->{'cfItem_type'} =~ /$SYNCHRONIZATION/ and $_->{'cfItem_type'} =~ /$SOURCE/){ if (exists($_->{relation_list}->[0]->{params_ci_1}->{Value}->{0}->{'Primary sync ref'}) and $_->{relation_list}->[0]->{params_ci_1}->{Value}->{0}->{'Primary sync ref'}->{value} =~ /true/){ $self->{testPNTPHash} = $_; } else { $self->{testSNTPHash} = $_; } } } return $self; }
3.取值的共通方法
sub _getCiAttributes{ my ( $self, $ci, $attribs ) = @_; #print "$ci\n"; #print "$attribs\n"; my $ref = ""; switch($ci){ case "$ENODEB" { die "Not find ENODEB attributes\n" unless $self->{testRbsHash}; $ref = $self->{testRbsHash}; } case "$CABINET" { die "Not find Cabinet attributes\n" unless $self->{testCabinetHash}; $ref = $self->{testCabinetHash}; } case "$TELNET" { die "Not find telnet switch attributes\n" unless $self->{testSwitchHash}; $ref = $self->{testSwitchHash}; } case "$MDU" { die "Not find master Du attributes\n" unless $self->{testMduHash}; $ref = $self->{testMduHash}; } } foreach ( @{ $attribs } ) { $ref = $ref->[ 0 ] if ( ref( $ref ) eq 'ARRAY' ); $ref = $ref->{ $_ }; } return $ref; }
4.供包外调用的方法,只举一例
sub getSwitchPort{ #my($funcName) = shift; my($self) = @_; return $self->_getCiAttributes("$TELNET",['relation_list','params_ci_1','Port']); }