Modify Q-Bridge methods to work on both pre-Enhanced Layer 2 Software (ELS) such as EX4200 and newer Enhanced Layer 2 Software (ELS) based switches such as EX4300 and QFX series
		
			
				
	
	
		
			858 lines
		
	
	
		
			27 KiB
		
	
	
	
		
			Perl
		
	
	
	
	
	
			
		
		
	
	
			858 lines
		
	
	
		
			27 KiB
		
	
	
	
		
			Perl
		
	
	
	
	
	
| # Test::SNMP::Info::Layer3::Juniper
 | |
| #
 | |
| # Copyright (c) 2018 Eric Miller
 | |
| # All rights reserved.
 | |
| #
 | |
| # Redistribution and use in source and binary forms, with or without
 | |
| # modification, are permitted provided that the following conditions are met:
 | |
| #
 | |
| #     * Redistributions of source code must retain the above copyright notice,
 | |
| #       this list of conditions and the following disclaimer.
 | |
| #     * Redistributions in binary form must reproduce the above copyright
 | |
| #       notice, this list of conditions and the following disclaimer in the
 | |
| #       documentation and/or other materials provided with the distribution.
 | |
| #     * Neither the name of the University of California, Santa Cruz nor the
 | |
| #       names of its contributors may be used to endorse or promote products
 | |
| #       derived from this software without specific prior written permission.
 | |
| #
 | |
| # THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
 | |
| # AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
 | |
| # IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
 | |
| # ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE
 | |
| # LIABLE FOR # ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
 | |
| # CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
 | |
| # SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
 | |
| # INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
 | |
| # CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
 | |
| # ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
 | |
| # POSSIBILITY OF SUCH DAMAGE.
 | |
| 
 | |
| package Test::SNMP::Info::Layer3::Juniper;
 | |
| 
 | |
| use Test::Class::Most parent => 'My::Test::Class';
 | |
| 
 | |
| use SNMP::Info::Layer3::Juniper;
 | |
| 
 | |
| sub setup : Tests(setup) {
 | |
|   my $test = shift;
 | |
|   $test->SUPER::setup;
 | |
| 
 | |
|   # Start with a common cache that will serve most tests
 | |
|   my $d_string = 'Juniper Networks, Inc. ex4200-24t internet router, ';
 | |
|   $d_string .= 'kernel JUNOS 10.4R6.5 ';
 | |
| 
 | |
|   my $cache_data = {
 | |
|     '_layers'      => 6,
 | |
|     '_description' => $d_string,
 | |
| 
 | |
|     # JUNIPER-CHASSIS-DEFINES-MIB::jnxProductNameEX4200
 | |
|     '_id'                      => '.1.3.6.1.4.1.2636.1.1.1.2.31',
 | |
|     '_version'                 => '14.1X53-D40.8',
 | |
|     '_serial'                  => 'AB0123456789',
 | |
|     '_jnxExVlanPortAccessMode' => 1,
 | |
|     '_jnx_v_name'              => 1,
 | |
|     '_jnx_v_index'             => 1,
 | |
|     '_jnx_v_type'              => 1,
 | |
| 
 | |
|     # Newer table doesn't exist in EX4200, but in cache to simplify testing
 | |
|     # method code
 | |
|     '_jnx_els_v_name'   => 1,
 | |
|     '_jnx_els_v_index'  => 1,
 | |
|     '_jnx_els_v_type'   => 1,
 | |
|     '_jnx_els_v_fdb_id' => 1,
 | |
|     '_bp_index'         => 1,
 | |
|     '_qb_i_vlan'        => 1,
 | |
|     '_qb_v_egress'      => 1,
 | |
|     '_qb_v_untagged'    => 1,
 | |
|     '_qb_fw_port'       => 1,
 | |
| 
 | |
|     # For pseudo entity testing
 | |
|     '_box_descr'                   => 'Juniper Virtual Chassis Ethernet Switch',
 | |
|     '_jnxVirtualChassisMemberRole' => 'master',
 | |
|     '_jnxContainersWithin'         => 1,
 | |
|     '_jnxContentsDescr'            => 1,
 | |
|     '_jnxContentsSerialNo'         => 1,
 | |
|     '_jnxFruType'                  => 1,
 | |
|     '_jnxContainersDescr'          => 1,
 | |
|     '_e_containers_type'           => 1,
 | |
|     '_jnxContentsPartNo'           => 1,
 | |
|     '_e_contents_type'             => 1,
 | |
|     '_jnxContainersWithin'         => 1,
 | |
| 
 | |
| 
 | |
|     'store' => {
 | |
|       'jnxExVlanPortAccessMode' => {'2.514' => 'access', '7.513' => 'trunk'},
 | |
|       'jnx_v_name'  => {2 => 'default', 3 => 'management'},
 | |
|       'jnx_v_index' => {2 => 0,         3 => 120},
 | |
|       'jnx_v_type'  => {2 => 'static',  3 => 'static'},
 | |
| 
 | |
|       # Newer table doesn't exist in EX4200, but in cache to simplify testing
 | |
|       # method code
 | |
|       'jnx_els_v_name' =>
 | |
|         {6 => 'VLAN0114_VPN78087', 7 => 'VLAN2088_VPN78117', 8 => 'default'},
 | |
|       'jnx_els_v_index'  => {6 => 114,      7   => 2088,     8   => 1},
 | |
|       'jnx_els_v_type'   => {6 => 'static', 7   => 'static', 8   => 'static'},
 | |
|       'jnx_els_v_fdb_id' => {6 => 393216,   7   => 458752,   8   => 524288},
 | |
|       'bp_index'         => {4 => 662,      491 => 509,      492 => 510},
 | |
|       'qb_i_vlan'        => {4 => 0,        491 => 113,      492 => 2088},
 | |
|       'qb_v_egress'   => {114 => '4', 2088 => '491,492'},
 | |
|       'qb_v_untagged' => {114 => '4', 2088 => '491,492'},
 | |
|       'qb_fw_port' =>
 | |
|         {'393216.0.19.149.30.221.37' => 4, '458752.0.9.245.16.59.121' => 492},
 | |
| 
 | |
|       'jnxContainersWithin' => {1 => 0, 2 => 1, 4 => 1, 7 => 1, 8 => 7, 9 => 1},
 | |
|       'jnxContentsDescr'    => {
 | |
|         '1.1.0.0' => '',
 | |
|         '2.1.1.0' => 'Power Supply: Power Supply 0 @ 0/0/*',
 | |
|         '2.1.2.0' => 'Power Supply: Power Supply 1 @ 0/1/*',
 | |
|         '2.2.1.0' => 'Power Supply: Power Supply 0 @ 1/0/*',
 | |
|         '2.2.2.0' => 'Power Supply: Power Supply 1 @ 1/1/*',
 | |
|         '4.1.1.1' => 'FAN 0 @ 0/0/0',
 | |
|         '4.1.2.1' => 'FAN 1 @ 0/1/0',
 | |
|         '4.2.1.1' => 'FAN 0 @ 1/0/0',
 | |
|         '4.2.2.1' => 'FAN 1 @ 1/1/0',
 | |
|         '7.1.0.0' => 'FPC: EX4300-48T @ 0/*/*',
 | |
|         '7.2.0.0' => 'FPC: EX4300-48T @ 1/*/*',
 | |
|         '8.1.1.0' => 'PIC: 48x 10/100/1000 Base-T @ 0/0/*',
 | |
|         '8.1.2.0' => 'PIC: 4x 40GE QSFP+ @ 0/1/*',
 | |
|         '8.1.3.0' => 'PIC: 4x 1G/10G SFP/SFP+ @ 0/2/*',
 | |
|         '8.2.1.0' => 'PIC: 48x 10/100/1000 Base-T @ 1/0/*',
 | |
|         '8.2.2.0' => 'PIC: 4x 40GE QSFP+ @ 1/1/*',
 | |
|         '8.2.3.0' => 'PIC: 4x 1G/10G SFP/SFP+ @ 1/2/*',
 | |
|         '9.1.0.0' => 'Routing Engine 0',
 | |
|         '9.2.0.0' => 'Routing Engine 1'
 | |
|       },
 | |
|       'jnxContentsSerialNo' => {
 | |
|         '2.1.1.0' => '1EDD1234567',
 | |
|         '2.1.2.0' => '1EDD2345678',
 | |
|         '2.2.1.0' => '1EDD3456789',
 | |
|         '2.2.2.0' => '1EDD4567890',
 | |
|         '7.1.0.0' => 'PE1234567890',
 | |
|         '7.2.0.0' => 'PE0123456789',
 | |
|         '8.1.1.0' => 'BUILTIN',
 | |
|         '8.1.2.0' => 'BUILTIN',
 | |
|         '8.1.3.0' => 'MY1234567890',
 | |
|         '8.2.1.0' => 'BUILTIN',
 | |
|         '8.2.2.0' => 'BUILTIN',
 | |
|         '8.2.3.0' => 'MY0123456789',
 | |
|         '9.1.0.0' => 'PE2345678901',
 | |
|         '9.2.0.0' => 'PE3456789012'
 | |
|       },
 | |
|       'jnxFruType' => {
 | |
|         '2.1.1.0' => 'powerEntryModule',
 | |
|         '2.1.2.0' => 'powerEntryModule',
 | |
|         '2.2.1.0' => 'powerEntryModule',
 | |
|         '2.2.2.0' => 'powerEntryModule',
 | |
|         '4.1.1.1' => 'fan',
 | |
|         '4.1.2.1' => 'fan',
 | |
|         '4.2.1.1' => 'fan',
 | |
|         '4.2.2.1' => 'fan',
 | |
|         '7.1.0.0' => 'flexiblePicConcentrator',
 | |
|         '7.2.0.0' => 'flexiblePicConcentrator',
 | |
|         '8.1.1.0' => 'portInterfaceCard',
 | |
|         '8.1.2.0' => 'portInterfaceCard',
 | |
|         '8.1.3.0' => 'portInterfaceCard',
 | |
|         '8.2.1.0' => 'portInterfaceCard',
 | |
|         '8.2.2.0' => 'portInterfaceCard',
 | |
|         '8.2.3.0' => 'portInterfaceCard',
 | |
|         '9.1.0.0' => 'routingEngine',
 | |
|         '9.2.0.0' => 'routingEngine'
 | |
|       },
 | |
|       'jnxContentsPartNo' => {
 | |
|         '2.1.1.0' => '740-046876',
 | |
|         '2.1.2.0' => '740-046876',
 | |
|         '2.2.1.0' => '740-046876',
 | |
|         '2.2.2.0' => '740-046876',
 | |
|         '7.1.0.0' => '650-044932',
 | |
|         '7.2.0.0' => '650-044932',
 | |
|         '8.1.1.0' => 'BUILTIN',
 | |
|         '8.1.2.0' => 'BUILTIN',
 | |
|         '8.1.3.0' => '611-063980',
 | |
|         '8.2.1.0' => 'BUILTIN',
 | |
|         '8.2.2.0' => 'BUILTIN',
 | |
|         '8.2.3.0' => '611-063980',
 | |
|         '9.1.0.0' => '650-044932',
 | |
|         '9.2.0.0' => '650-044932'
 | |
|       },
 | |
| 
 | |
|       # These are cached raw
 | |
|       'e_contents_type' => {
 | |
|         '1.1.0.0' => '.1.3.6.1.4.1.2636.1.1.2.1.63.0',
 | |
|         '2.1.1.0' => '.1.3.6.1.4.1.2636.1.1.3.2.63.1.1.0',
 | |
|         '2.1.2.0' => '.1.3.6.1.4.1.2636.1.1.3.2.63.1.1.0',
 | |
|         '2.2.1.0' => '.1.3.6.1.4.1.2636.1.1.3.2.63.1.1.0',
 | |
|         '2.2.2.0' => '.1.3.6.1.4.1.2636.1.1.3.2.63.1.1.0',
 | |
|         '4.1.1.1' => '.1.3.6.1.4.1.2636.1.1.3.2.63.1.2.0',
 | |
|         '4.1.2.1' => '.1.3.6.1.4.1.2636.1.1.3.2.63.1.2.0',
 | |
|         '4.2.1.1' => '.1.3.6.1.4.1.2636.1.1.3.2.63.1.2.0',
 | |
|         '4.2.2.1' => '.1.3.6.1.4.1.2636.1.1.3.2.63.1.2.0',
 | |
|         '7.1.0.0' => '.1.3.6.1.4.1.2636.1.1.3.2.63.1.0',
 | |
|         '7.2.0.0' => '.1.3.6.1.4.1.2636.1.1.3.2.63.1.0',
 | |
|         '8.1.1.0' => '.1.3.6.1.4.1.2636.1.1.1.4.63.2.0',
 | |
|         '8.1.2.0' => '.1.3.6.1.4.1.2636.1.1.3.3.12.1.319.0',
 | |
|         '8.1.3.0' => '.1.3.6.1.4.1.2636.1.1.3.3.12.1.320.0',
 | |
|         '8.2.1.0' => '.1.3.6.1.4.1.2636.1.1.1.4.63.2.0',
 | |
|         '8.2.2.0' => '.1.3.6.1.4.1.2636.1.1.3.3.12.1.319.0',
 | |
|         '8.2.3.0' => '.1.3.6.1.4.1.2636.1.1.3.3.12.1.320.0',
 | |
|         '9.1.0.0' => '.1.3.6.1.4.1.2636.1.1.2.1.63.1.0',
 | |
|         '9.2.0.0' => '.1.3.6.1.4.1.2636.1.1.2.1.63.1.0'
 | |
|       },
 | |
|       'jnxContainersDescr' => {
 | |
|         1 => 'chassis frame',
 | |
|         2 => 'Power Supply slot',
 | |
|         4 => 'FAN slot',
 | |
|         7 => 'FPC slot',
 | |
|         8 => 'PIC slot',
 | |
|         9 => 'Routing Engine slot'
 | |
|       },
 | |
| 
 | |
|       # These are cached raw
 | |
|       'e_containers_type' => {
 | |
|         1 => '.1.3.6.1.4.1.2636.1.1.2.1.63.0',
 | |
|         2 => '.1.3.6.1.4.1.2636.1.1.2.2.63.1.1.0',
 | |
|         4 => '.1.3.6.1.4.1.2636.1.1.2.2.63.1.2.0',
 | |
|         7 => '.1.3.6.1.4.1.2636.1.1.2.2.63.1.0',
 | |
|         8 => '.1.3.6.1.4.1.2636.1.1.2.3.63.1.0',
 | |
|         9 => '.1.3.6.1.4.1.2636.1.1.2.1.63.1.0'
 | |
|       },
 | |
|       'jnxContainersWithin' => {1 => 0, 2 => 1, 4 => 1, 7 => 1, 8 => 7, 9 => 1}
 | |
|     }
 | |
|   };
 | |
|   $test->{info}->cache($cache_data);
 | |
| }
 | |
| 
 | |
| sub vendor : Tests(2) {
 | |
|   my $test = shift;
 | |
| 
 | |
|   can_ok($test->{info}, 'vendor');
 | |
|   is($test->{info}->vendor(), 'juniper', q(Vendor returns 'juniper'));
 | |
| }
 | |
| 
 | |
| sub os : Tests(2) {
 | |
|   my $test = shift;
 | |
| 
 | |
|   can_ok($test->{info}, 'os');
 | |
|   is($test->{info}->os(), 'junos', q(OS returns 'junos'));
 | |
| }
 | |
| 
 | |
| sub layers : Tests(5) {
 | |
|   my $test = shift;
 | |
| 
 | |
|   can_ok($test->{info}, 'layers');
 | |
|   is($test->{info}->layers(), '00000110', q(Original layers unmodified));
 | |
| 
 | |
|   # Set to layer 3 only and with presence of FDB 'qb_fw_port' will turn on
 | |
|   # layer 2
 | |
|   $test->{info}{_layers} = 4;
 | |
|   is($test->{info}->layers(),
 | |
|     '00000110', q(Layer2 added due to presence of FDB));
 | |
| 
 | |
|   # Delete FDB cache flag, layers still = 4 binary (3 only)
 | |
|   delete $test->{info}{_qb_fw_port};
 | |
|   is($test->{info}->layers(), '00000100', q(No layer2 without FDB));
 | |
| 
 | |
|   $test->{info}->clear_cache();
 | |
|   is($test->{info}->layers(), undef, q(No data returns undef layers));
 | |
| }
 | |
| 
 | |
| sub os_ver : Tests(5) {
 | |
|   my $test = shift;
 | |
| 
 | |
|   can_ok($test->{info}, 'os_ver');
 | |
|   is($test->{info}->os_ver(),
 | |
|     '14.1X53-D40.8',
 | |
|     q(OS version returned from 'jnxVirtualChassisMemberSWVersion'));
 | |
| 
 | |
|   delete $test->{info}{_version};
 | |
|   is($test->{info}->os_ver(),
 | |
|     '10.4R6.5', q(OS version returned from 'sysDescr'));
 | |
| 
 | |
|   delete $test->{info}{_description};
 | |
|   $test->{info}{_lldp_sysdesc}
 | |
|     = 'Juniper Networks, Inc. srx240h-poe , version 12.1R3.5 Build date: ';
 | |
|   is($test->{info}->os_ver(),
 | |
|     '12.1R3.5', q(OS version returned from 'lldpLocSysDesc'));
 | |
| 
 | |
|   $test->{info}->clear_cache();
 | |
|   is($test->{info}->os_ver(), undef, q(No data returns undef OS version));
 | |
| }
 | |
| 
 | |
| sub model : Tests(4) {
 | |
|   my $test = shift;
 | |
| 
 | |
|   can_ok($test->{info}, 'model');
 | |
|   is($test->{info}->model(), 'EX4200', q(Model translates id));
 | |
| 
 | |
|   $test->{info}{_id} = '.100.3.6.1.4.1.6527.1.3.1';
 | |
|   is($test->{info}->model(), '.100.3.6.1.4.1.6527.1.3.1', q(Model uses id));
 | |
| 
 | |
|   $test->{info}{_vc_model} = 'qfx5100-48s-6q';
 | |
|   is($test->{info}->model(),
 | |
|     'QFX5100-48S-6Q', q(Model uses 'jnxVirtualChassisMemberModel'));
 | |
| }
 | |
| 
 | |
| sub serial : Tests(3) {
 | |
|   my $test = shift;
 | |
| 
 | |
|   can_ok($test->{info}, 'serial');
 | |
|   is($test->{info}->serial(),
 | |
|     'AB0123456789', q(Serial returns 'jnxBoxSerialNo'));
 | |
| 
 | |
|   $test->{info}->clear_cache();
 | |
|   is($test->{info}->serial(), undef, q(No data returns undef serial));
 | |
| }
 | |
| 
 | |
| sub i_trunk : Tests(3) {
 | |
|   my $test = shift;
 | |
| 
 | |
|   can_ok($test->{info}, 'i_trunk');
 | |
| 
 | |
|   my $expected = {'514' => 'access', '513' => 'trunk'};
 | |
|   cmp_deeply($test->{info}->i_trunk(),
 | |
|     $expected, q(Interface trunk status returns expected values));
 | |
| 
 | |
|   $test->{info}->clear_cache();
 | |
|   cmp_deeply($test->{info}->i_trunk(), {}, q(No data returns empty hash));
 | |
| }
 | |
| 
 | |
| sub qb_fdb_index : Tests(4) {
 | |
|   my $test = shift;
 | |
| 
 | |
|   can_ok($test->{info}, 'qb_fdb_index');
 | |
| 
 | |
|   my $expected = {393216 => 114, 458752 => 2088, 524288 => 1};
 | |
|   cmp_deeply($test->{info}->qb_fdb_index(),
 | |
|     $expected, q(ELS VLAN to FDB index returned expected values));
 | |
| 
 | |
|   delete $test->{info}{'_jnx_els_v_index'};
 | |
|   $expected = {2 => 0, 3 => 120};
 | |
|   cmp_deeply($test->{info}->qb_fdb_index(),
 | |
|     $expected, q(Older VLAN to FDB index returned expected values));
 | |
| 
 | |
|   $test->{info}->clear_cache();
 | |
|   cmp_deeply($test->{info}->qb_fdb_index(), undef, q(No data returns undef));
 | |
| }
 | |
| 
 | |
| sub v_type : Tests(4) {
 | |
|   my $test = shift;
 | |
| 
 | |
|   can_ok($test->{info}, 'v_type');
 | |
| 
 | |
|   my $expected = {6 => 'static', 7 => 'static', 8 => 'static'};
 | |
|   cmp_deeply($test->{info}->v_type(),
 | |
|     $expected, q(ELS VLAN types returned expected values));
 | |
| 
 | |
|   delete $test->{info}{'_jnx_els_v_type'};
 | |
|   $expected = {2 => 'static', 3 => 'static'};
 | |
|   cmp_deeply($test->{info}->v_type(),
 | |
|     $expected, q(Older VLAN types returned expected values));
 | |
| 
 | |
|   $test->{info}->clear_cache();
 | |
|   cmp_deeply($test->{info}->v_type(), undef, q(No data returns undef));
 | |
| }
 | |
| 
 | |
| sub v_index : Tests(4) {
 | |
|   my $test = shift;
 | |
| 
 | |
|   can_ok($test->{info}, 'v_index');
 | |
| 
 | |
|   my $expected = {6 => 114, 7 => 2088, 8 => 1};
 | |
|   cmp_deeply($test->{info}->v_index(),
 | |
|     $expected, q(ELS VLAN index returned expected values));
 | |
| 
 | |
|   delete $test->{info}{'_jnx_els_v_index'};
 | |
|   $expected = {2 => 0, 3 => 120};
 | |
|   cmp_deeply($test->{info}->v_index(),
 | |
|     $expected, q(Older VLAN index returned expected values));
 | |
| 
 | |
|   $test->{info}->clear_cache();
 | |
|   cmp_deeply($test->{info}->v_index(), undef, q(No data returns undef));
 | |
| }
 | |
| 
 | |
| sub i_vlan : Tests(4) {
 | |
|   my $test = shift;
 | |
| 
 | |
|   can_ok($test->{info}, 'i_vlan');
 | |
| 
 | |
|   my $expected = {662 => 0, 509 => 113, 510 => 2088};
 | |
|   cmp_deeply($test->{info}->i_vlan(),
 | |
|     $expected, q(ELS PVID returned expected values));
 | |
| 
 | |
|   delete $test->{info}{'_jnx_els_v_index'};
 | |
|   $test->{info}{store}{bp_index}  = {513 => 505, 514 => 507};
 | |
|   $test->{info}{store}{qb_i_vlan} = {513 => 3,   514 => 2};
 | |
|   $expected                       = {505 => 120, 507 => 0};
 | |
|   cmp_deeply($test->{info}->i_vlan(),
 | |
|     $expected, q(Older PVID returned expected values));
 | |
| 
 | |
|   $test->{info}->clear_cache();
 | |
|   cmp_deeply($test->{info}->i_vlan(), {}, q(No data returns empty hash));
 | |
| }
 | |
| 
 | |
| sub v_name : Tests(4) {
 | |
|   my $test = shift;
 | |
| 
 | |
|   can_ok($test->{info}, 'v_name');
 | |
| 
 | |
|   my $expected
 | |
|     = {6 => 'VLAN0114_VPN78087', 7 => 'VLAN2088_VPN78117', 8 => 'default'};
 | |
|   cmp_deeply($test->{info}->v_name(),
 | |
|     $expected, q(ELS VLAN names returned expected values));
 | |
| 
 | |
|   delete $test->{info}{'_jnx_els_v_name'};
 | |
|   $expected = {2 => 'default', 3 => 'management'};
 | |
|   cmp_deeply($test->{info}->v_name(),
 | |
|     $expected, q(Older VLAN names returned expected values));
 | |
| 
 | |
|   $test->{info}->clear_cache();
 | |
|   cmp_deeply($test->{info}->v_name(), undef, q(No data returns undef));
 | |
| }
 | |
| 
 | |
| sub i_vlan_membership : Tests(4) {
 | |
|   my $test = shift;
 | |
| 
 | |
|   can_ok($test->{info}, 'i_vlan_membership');
 | |
| 
 | |
|   # Delete this so we can test new method first
 | |
|   delete $test->{info}{'_jnx_v_index'};
 | |
| 
 | |
|   my $expected = {662 => [114], 509 => [2088], 510 => [2088]};
 | |
|   cmp_deeply($test->{info}->i_vlan_membership(),
 | |
|     $expected, q(ELS VLAN membership returned expected values));
 | |
| 
 | |
|   # Restore so we can trigger test for older devices
 | |
|   $test->{info}{'_jnx_v_index'} = 1;
 | |
|   delete $test->{info}{'_jnx_els_v_index'};
 | |
| 
 | |
|   my $padding = '00000000000000000000000000000000' x 4;
 | |
| 
 | |
|   # This has bits 516 - 536 on
 | |
|   my $portlist2 = $padding . '1FFFFF';
 | |
| 
 | |
|   # This has bits 512 - 515 on
 | |
|   my $portlist3 = $padding . 'E0';
 | |
| 
 | |
|   # To simplify the expected value, we're only going to define the mapping
 | |
|   # for five ports
 | |
|   $test->{info}{store}{bp_index}
 | |
|     = {513 => 505, 514 => 507, 515 => 509, 516 => 511, 536 => 551};
 | |
|   $test->{info}{store}{qb_v_egress}
 | |
|     = {2 => pack("H*", $portlist2), 3 => pack("H*", $portlist3)};
 | |
| 
 | |
|   $expected
 | |
|     = {505 => [120], 507 => [120], 509 => [120], 511 => [0], 551 => [0]};
 | |
|   cmp_deeply($test->{info}->i_vlan_membership(),
 | |
|     $expected, q(VLAN membership returned expected values));
 | |
| 
 | |
|   $test->{info}->clear_cache();
 | |
|   cmp_deeply($test->{info}->i_vlan_membership(),
 | |
|     undef, q(No data returns undef));
 | |
| }
 | |
| 
 | |
| # Same code as i_vlan_membership, untagged just uses different leaf
 | |
| sub i_vlan_membership_untagged : Tests(4) {
 | |
|   my $test = shift;
 | |
| 
 | |
|   can_ok($test->{info}, 'i_vlan_membership_untagged');
 | |
| 
 | |
|   # Delete this so we can test new method first
 | |
|   delete $test->{info}{'_jnx_v_index'};
 | |
| 
 | |
|   my $expected = {662 => [114], 509 => [2088], 510 => [2088]};
 | |
|   cmp_deeply($test->{info}->i_vlan_membership_untagged(),
 | |
|     $expected, q(ELS VLAN membership untagged returned expected values));
 | |
| 
 | |
|   # Restore so we can trigger test for older devices
 | |
|   $test->{info}{'_jnx_v_index'} = 1;
 | |
|   delete $test->{info}{'_jnx_els_v_index'};
 | |
| 
 | |
|   my $padding = '00000000000000000000000000000000' x 4;
 | |
| 
 | |
|   # This has bits 516 - 536 on
 | |
|   my $portlist2 = $padding . '1FFFFF';
 | |
| 
 | |
|   # This has bits 512 - 515 on
 | |
|   my $portlist3 = $padding . 'E0';
 | |
| 
 | |
|   # To simplify the expected value, we're only going to define the mapping
 | |
|   # for five ports
 | |
|   $test->{info}{store}{bp_index}
 | |
|     = {513 => 505, 514 => 507, 515 => 509, 516 => 511, 536 => 551};
 | |
|   $test->{info}{store}{qb_v_untagged}
 | |
|     = {2 => pack("H*", $portlist2), 3 => pack("H*", $portlist3)};
 | |
| 
 | |
|   $expected
 | |
|     = {505 => [120], 507 => [120], 509 => [120], 511 => [0], 551 => [0]};
 | |
|   cmp_deeply($test->{info}->i_vlan_membership_untagged(),
 | |
|     $expected, q(VLAN membership untagged returned expected values));
 | |
| 
 | |
|   $test->{info}->clear_cache();
 | |
|   cmp_deeply($test->{info}->i_vlan_membership_untagged(),
 | |
|     undef, q(No data returns undef));
 | |
| }
 | |
| 
 | |
| # These is no longer defined in the class, but tested due to past issues with
 | |
| # VLAN mapping due to changes with the introduction of ELS. See issue #67
 | |
| # Juniper EX4300 Missing/Wrong information #67
 | |
| sub qb_fw_vlan : Tests(4) {
 | |
|   my $test = shift;
 | |
| 
 | |
|   can_ok($test->{info}, 'qb_fw_vlan');
 | |
| 
 | |
|   my $expected
 | |
|     = {'393216.0.19.149.30.221.37' => 114, '458752.0.9.245.16.59.121' => 2088};
 | |
|   cmp_deeply($test->{info}->qb_fw_vlan(),
 | |
|     $expected,
 | |
|     q(ELS forwarding table entries to VLAN IDs returned expected values));
 | |
| 
 | |
|   delete $test->{info}{'_jnx_els_v_index'};
 | |
|   $test->{info}{store}{qb_fw_port}
 | |
|     = {'2.0.19.149.30.221.37' => 513, '3.0.9.245.16.59.121' => 507};
 | |
|   $expected = {'2.0.19.149.30.221.37' => 0, '3.0.9.245.16.59.121' => 120};
 | |
|   cmp_deeply($test->{info}->qb_fw_vlan(),
 | |
|     $expected,
 | |
|     q(Older forwarding table entries to VLAN IDs returned expected values));
 | |
| 
 | |
|   $test->{info}->clear_cache();
 | |
|   cmp_deeply($test->{info}->qb_fw_vlan(), {}, q(No data returns empty hash));
 | |
| }
 | |
| 
 | |
| sub e_index : Tests(3) {
 | |
|   my $test = shift;
 | |
| 
 | |
|   can_ok($test->{info}, 'e_index');
 | |
| 
 | |
|   my $expected = {
 | |
|     '1'       => '01000000',
 | |
|     '1.1.0.0' => '01010000',
 | |
|     '2'       => '02000000',
 | |
|     '2.1.1.0' => '02010100',
 | |
|     '2.1.2.0' => '02010200',
 | |
|     '2.2.1.0' => '02020100',
 | |
|     '2.2.2.0' => '02020200',
 | |
|     '4'       => '04000000',
 | |
|     '4.1.1.1' => '04010101',
 | |
|     '4.1.2.1' => '04010201',
 | |
|     '4.2.1.1' => '04020101',
 | |
|     '4.2.2.1' => '04020201',
 | |
|     '7'       => '07000000',
 | |
|     '7.1.0.0' => '07010000',
 | |
|     '7.2.0.0' => '07020000',
 | |
|     '8'       => '08000000',
 | |
|     '8.1.1.0' => '08010100',
 | |
|     '8.1.2.0' => '08010200',
 | |
|     '8.1.3.0' => '08010300',
 | |
|     '8.2.1.0' => '08020100',
 | |
|     '8.2.2.0' => '08020200',
 | |
|     '8.2.3.0' => '08020300',
 | |
|     '9'       => '09000000',
 | |
|     '9.1.0.0' => '09010000',
 | |
|     '9.2.0.0' => '09020000'
 | |
|   };
 | |
|   cmp_deeply($test->{info}->e_index(),
 | |
|     $expected, q(Entity index returned expected values));
 | |
| 
 | |
|   $test->{info}->clear_cache();
 | |
|   cmp_deeply($test->{info}->e_index(), {}, q(No data returns empty hash));
 | |
| }
 | |
| 
 | |
| sub e_class : Tests(3) {
 | |
|   my $test = shift;
 | |
| 
 | |
|   can_ok($test->{info}, 'e_class');
 | |
| 
 | |
|   my $expected = {
 | |
|     '1'       => 'chassis',
 | |
|     '1.1.0.0' => 'container',
 | |
|     '2'       => 'container',
 | |
|     '2.1.1.0' => 'powerSupply',
 | |
|     '2.1.2.0' => 'powerSupply',
 | |
|     '2.2.1.0' => 'powerSupply',
 | |
|     '2.2.2.0' => 'powerSupply',
 | |
|     '4'       => 'container',
 | |
|     '4.1.1.1' => 'fan',
 | |
|     '4.1.2.1' => 'fan',
 | |
|     '4.2.1.1' => 'fan',
 | |
|     '4.2.2.1' => 'fan',
 | |
|     '7'       => 'container',
 | |
|     '7.1.0.0' => 'module',
 | |
|     '7.2.0.0' => 'module',
 | |
|     '8'       => 'container',
 | |
|     '8.1.1.0' => 'module',
 | |
|     '8.1.2.0' => 'module',
 | |
|     '8.1.3.0' => 'module',
 | |
|     '8.2.1.0' => 'module',
 | |
|     '8.2.2.0' => 'module',
 | |
|     '8.2.3.0' => 'module',
 | |
|     '9'       => 'container',
 | |
|     '9.1.0.0' => 'module',
 | |
|     '9.2.0.0' => 'module'
 | |
|   };
 | |
|   cmp_deeply($test->{info}->e_class(),
 | |
|     $expected, q(Entity classes returned expected values));
 | |
| 
 | |
|   $test->{info}->clear_cache();
 | |
|   cmp_deeply($test->{info}->e_class(), {}, q(No data returns empty hash));
 | |
| }
 | |
| 
 | |
| sub e_descr : Tests(3) {
 | |
|   my $test = shift;
 | |
| 
 | |
|   can_ok($test->{info}, 'e_descr');
 | |
| 
 | |
|   my $expected = {
 | |
|     '1'       => 'Juniper Virtual Chassis Ethernet Switch',
 | |
|     '1.1.0.0' => 'chassis frame',
 | |
|     '2'       => 'Power Supply slot',
 | |
|     '2.1.1.0' => 'Power Supply: Power Supply 0 @ 0/0/*',
 | |
|     '2.1.2.0' => 'Power Supply: Power Supply 1 @ 0/1/*',
 | |
|     '2.2.1.0' => 'Power Supply: Power Supply 0 @ 1/0/*',
 | |
|     '2.2.2.0' => 'Power Supply: Power Supply 1 @ 1/1/*',
 | |
|     '4'       => 'FAN slot',
 | |
|     '4.1.1.1' => 'FAN 0 @ 0/0/0',
 | |
|     '4.1.2.1' => 'FAN 1 @ 0/1/0',
 | |
|     '4.2.1.1' => 'FAN 0 @ 1/0/0',
 | |
|     '4.2.2.1' => 'FAN 1 @ 1/1/0',
 | |
|     '7'       => 'FPC slot',
 | |
|     '7.1.0.0' => 'FPC: EX4300-48T @ 0/*/*',
 | |
|     '7.2.0.0' => 'FPC: EX4300-48T @ 1/*/*',
 | |
|     '8'       => 'PIC slot',
 | |
|     '8.1.1.0' => 'PIC: 48x 10/100/1000 Base-T @ 0/0/*',
 | |
|     '8.1.2.0' => 'PIC: 4x 40GE QSFP+ @ 0/1/*',
 | |
|     '8.1.3.0' => 'PIC: 4x 1G/10G SFP/SFP+ @ 0/2/*',
 | |
|     '8.2.1.0' => 'PIC: 48x 10/100/1000 Base-T @ 1/0/*',
 | |
|     '8.2.2.0' => 'PIC: 4x 40GE QSFP+ @ 1/1/*',
 | |
|     '8.2.3.0' => 'PIC: 4x 1G/10G SFP/SFP+ @ 1/2/*',
 | |
|     '9'       => 'Routing Engine slot',
 | |
|     '9.1.0.0' => 'Routing Engine 0',
 | |
|     '9.2.0.0' => 'Routing Engine 1'
 | |
|   };
 | |
|   cmp_deeply($test->{info}->e_descr(),
 | |
|     $expected, q(Entity descriptions returned expected values));
 | |
| 
 | |
|   $test->{info}->clear_cache();
 | |
|   cmp_deeply($test->{info}->e_descr(), {}, q(No data returns empty hash));
 | |
| }
 | |
| 
 | |
| sub e_serial : Tests(3) {
 | |
|   my $test = shift;
 | |
| 
 | |
|   can_ok($test->{info}, 'e_serial');
 | |
| 
 | |
|   my $expected = {
 | |
|     '1'       => 'AB0123456789',
 | |
|     '2.1.1.0' => '1EDD1234567',
 | |
|     '2.1.2.0' => '1EDD2345678',
 | |
|     '2.2.1.0' => '1EDD3456789',
 | |
|     '2.2.2.0' => '1EDD4567890',
 | |
|     '7.1.0.0' => 'PE1234567890',
 | |
|     '7.2.0.0' => 'PE0123456789',
 | |
|     '8.1.3.0' => 'MY1234567890',
 | |
|     '8.2.3.0' => 'MY0123456789',
 | |
|     '9.1.0.0' => 'PE2345678901',
 | |
|     '9.2.0.0' => 'PE3456789012'
 | |
|   };
 | |
|   cmp_deeply($test->{info}->e_serial(),
 | |
|     $expected, q(Entity serial numbers returned expected values));
 | |
| 
 | |
|   $test->{info}->clear_cache();
 | |
|   cmp_deeply($test->{info}->e_serial(), {}, q(No data returns empty hash));
 | |
| }
 | |
| 
 | |
| sub e_fru : Tests(3) {
 | |
|   my $test = shift;
 | |
| 
 | |
|   can_ok($test->{info}, 'e_fru');
 | |
| 
 | |
|   my $expected = {
 | |
|     '1'       => 'false',
 | |
|     '1.1.0.0' => 'false',
 | |
|     '2'       => 'false',
 | |
|     '2.1.1.0' => 'true',
 | |
|     '2.1.2.0' => 'true',
 | |
|     '2.2.1.0' => 'true',
 | |
|     '2.2.2.0' => 'true',
 | |
|     '4'       => 'false',
 | |
|     '4.1.1.1' => 'false',
 | |
|     '4.1.2.1' => 'false',
 | |
|     '4.2.1.1' => 'false',
 | |
|     '4.2.2.1' => 'false',
 | |
|     '7'       => 'false',
 | |
|     '7.1.0.0' => 'true',
 | |
|     '7.2.0.0' => 'true',
 | |
|     '8'       => 'false',
 | |
|     '8.1.1.0' => 'false',
 | |
|     '8.1.2.0' => 'false',
 | |
|     '8.1.3.0' => 'true',
 | |
|     '8.2.1.0' => 'false',
 | |
|     '8.2.2.0' => 'false',
 | |
|     '8.2.3.0' => 'true',
 | |
|     '9'       => 'false',
 | |
|     '9.1.0.0' => 'true',
 | |
|     '9.2.0.0' => 'true'
 | |
|   };
 | |
|   cmp_deeply($test->{info}->e_fru(),
 | |
|     $expected, q(Entity FRUs returned expected values));
 | |
| 
 | |
|   $test->{info}->clear_cache();
 | |
|   cmp_deeply($test->{info}->e_fru(), {}, q(No data returns empty hash));
 | |
| }
 | |
| 
 | |
| sub e_type : Tests(3) {
 | |
|   my $test = shift;
 | |
| 
 | |
|   can_ok($test->{info}, 'e_type');
 | |
| 
 | |
|   my $expected = {
 | |
|     '1'       => 'jnxChassisEX4300',
 | |
|     '2'       => 'jnxEX4300SlotPower',
 | |
|     '1.1.0.0' => 'jnxChassisEX4300',
 | |
|     '2.1.1.0' => 'jnxEX4300Power',
 | |
|     '2.1.2.0' => 'jnxEX4300Power',
 | |
|     '2.2.1.0' => 'jnxEX4300Power',
 | |
|     '2.2.2.0' => 'jnxEX4300Power',
 | |
|     '4'       => 'jnxEX4300SlotFan',
 | |
|     '4.1.1.1' => 'jnxEX4300Fan',
 | |
|     '4.1.2.1' => 'jnxEX4300Fan',
 | |
|     '4.2.1.1' => 'jnxEX4300Fan',
 | |
|     '4.2.2.1' => 'jnxEX4300Fan',
 | |
|     '7'       => 'jnxEX4300SlotFPC',
 | |
|     '7.1.0.0' => 'jnxEX4300FPC',
 | |
|     '7.2.0.0' => 'jnxEX4300FPC',
 | |
|     '8'       => 'jnxEX4300MediaCardSpacePIC',
 | |
|     '8.1.1.0' => 'jnxProductEX4300port48T',
 | |
|     '8.1.2.0' => 'jnxPicEX4300QSFP4Port',
 | |
|     '8.1.3.0' => 'jnxPicEX4300UplinkSFPPlus4Port',
 | |
|     '8.2.1.0' => 'jnxProductEX4300port48T',
 | |
|     '8.2.2.0' => 'jnxPicEX4300QSFP4Port',
 | |
|     '8.2.3.0' => 'jnxPicEX4300UplinkSFPPlus4Port',
 | |
|     '9'       => 'jnxEX4300RE0',
 | |
|     '9.1.0.0' => 'jnxEX4300RE0',
 | |
|     '9.2.0.0' => 'jnxEX4300RE0'
 | |
|   };
 | |
|   cmp_deeply($test->{info}->e_type(),
 | |
|     $expected, q(Entity types returned expected values));
 | |
| 
 | |
|   $test->{info}->clear_cache();
 | |
|   cmp_deeply($test->{info}->e_type(), {}, q(No data returns empty hash));
 | |
| }
 | |
| 
 | |
| sub e_vendor : Tests(3) {
 | |
|   my $test = shift;
 | |
| 
 | |
|   can_ok($test->{info}, 'e_vendor');
 | |
| 
 | |
|   my $expected = {
 | |
|     '1'       => 'juniper',
 | |
|     '2'       => 'juniper',
 | |
|     '1.1.0.0' => 'juniper',
 | |
|     '2.1.1.0' => 'juniper',
 | |
|     '2.1.2.0' => 'juniper',
 | |
|     '2.2.1.0' => 'juniper',
 | |
|     '2.2.2.0' => 'juniper',
 | |
|     '4'       => 'juniper',
 | |
|     '4.1.1.1' => 'juniper',
 | |
|     '4.1.2.1' => 'juniper',
 | |
|     '4.2.1.1' => 'juniper',
 | |
|     '4.2.2.1' => 'juniper',
 | |
|     '7'       => 'juniper',
 | |
|     '7.1.0.0' => 'juniper',
 | |
|     '7.2.0.0' => 'juniper',
 | |
|     '8'       => 'juniper',
 | |
|     '8.1.1.0' => 'juniper',
 | |
|     '8.1.2.0' => 'juniper',
 | |
|     '8.1.3.0' => 'juniper',
 | |
|     '8.2.1.0' => 'juniper',
 | |
|     '8.2.2.0' => 'juniper',
 | |
|     '8.2.3.0' => 'juniper',
 | |
|     '9'       => 'juniper',
 | |
|     '9.1.0.0' => 'juniper',
 | |
|     '9.2.0.0' => 'juniper'
 | |
|   };
 | |
|   cmp_deeply($test->{info}->e_vendor(),
 | |
|     $expected, q(Entity vendor returned expected values));
 | |
| 
 | |
|   $test->{info}->clear_cache();
 | |
|   cmp_deeply($test->{info}->e_vendor(), {}, q(No data returns empty hash));
 | |
| }
 | |
| 
 | |
| sub e_pos : Tests(3) {
 | |
|   my $test = shift;
 | |
| 
 | |
|   can_ok($test->{info}, 'e_pos');
 | |
| 
 | |
|   my $expected = {
 | |
|     '1'       => '01000000',
 | |
|     '1.1.0.0' => '01010000',
 | |
|     '2'       => '02000000',
 | |
|     '2.1.1.0' => '02010100',
 | |
|     '2.1.2.0' => '02010200',
 | |
|     '2.2.1.0' => '02020100',
 | |
|     '2.2.2.0' => '02020200',
 | |
|     '4'       => '04000000',
 | |
|     '4.1.1.1' => '04010101',
 | |
|     '4.1.2.1' => '04010201',
 | |
|     '4.2.1.1' => '04020101',
 | |
|     '4.2.2.1' => '04020201',
 | |
|     '7'       => '07000000',
 | |
|     '7.1.0.0' => '07010000',
 | |
|     '7.2.0.0' => '07020000',
 | |
|     '8'       => '08000000',
 | |
|     '8.1.1.0' => '08010100',
 | |
|     '8.1.2.0' => '08010200',
 | |
|     '8.1.3.0' => '08010300',
 | |
|     '8.2.1.0' => '08020100',
 | |
|     '8.2.2.0' => '08020200',
 | |
|     '8.2.3.0' => '08020300',
 | |
|     '9'       => '09000000',
 | |
|     '9.1.0.0' => '09010000',
 | |
|     '9.2.0.0' => '09020000'
 | |
|   };
 | |
|   cmp_deeply($test->{info}->e_pos(),
 | |
|     $expected, q(Entity position returned expected values));
 | |
| 
 | |
|   $test->{info}->clear_cache();
 | |
|   cmp_deeply($test->{info}->e_pos(), {}, q(No data returns empty hash));
 | |
| }
 | |
| 
 | |
| sub e_parent : Tests(3) {
 | |
|   my $test = shift;
 | |
| 
 | |
|   can_ok($test->{info}, 'e_parent');
 | |
| 
 | |
|   my $expected = {
 | |
|     '1'       => '00000000',
 | |
|     '1.1.0.0' => '01000000',
 | |
|     '2'       => '01000000',
 | |
|     '2.1.1.0' => '02000000',
 | |
|     '2.1.2.0' => '02000000',
 | |
|     '2.2.1.0' => '02000000',
 | |
|     '2.2.2.0' => '02000000',
 | |
|     '4'       => '01000000',
 | |
|     '4.1.1.1' => '04000000',
 | |
|     '4.1.2.1' => '04000000',
 | |
|     '4.2.1.1' => '04000000',
 | |
|     '4.2.2.1' => '04000000',
 | |
|     '7'       => '01000000',
 | |
|     '7.1.0.0' => '07000000',
 | |
|     '7.2.0.0' => '07000000',
 | |
|     '8'       => '07000000',
 | |
|     '8.1.1.0' => '08000000',
 | |
|     '8.1.2.0' => '08000000',
 | |
|     '8.1.3.0' => '08000000',
 | |
|     '8.2.1.0' => '08000000',
 | |
|     '8.2.2.0' => '08000000',
 | |
|     '8.2.3.0' => '08000000',
 | |
|     '9'       => '01000000',
 | |
|     '9.1.0.0' => '09000000',
 | |
|     '9.2.0.0' => '09000000'
 | |
|   };
 | |
|   cmp_deeply($test->{info}->e_parent(),
 | |
|     $expected, q(Entity parent returned expected values));
 | |
| 
 | |
|   $test->{info}->clear_cache();
 | |
|   cmp_deeply($test->{info}->e_parent(), {}, q(No data returns empty hash));
 | |
| }
 | |
| 
 | |
| 1;
 |