Learning and Testing Ansible Playbooks with Virtual Images

One of the common problems I see with network automation in general is that no one wants to learn and test their automation software on production network gear.  While lots of people have labs they can play with network gear that obviously is not an option for everyone.  Even used equipment can cost a thousand dollars or more, and in my case my spouse was not super excited about our power bill rising by $100 a month while I ran some Cisco switches in my office.  

I am not saying that owning networking hardware is a bad idea, its just not exactly scalable, and doesn’t work for everyone’s situation.  Imagine the network engineer living in New York City in the super small apartment. I was lucky enough while studying for my CCIE to have access to a lab at work where I had all the equipment I needed to play with, and didn’t have to deal with the heat, noise and power bills.  I was a Cisco employee at the time so I also had access to virtual Cisco images.

Luckily networking vendors (including Cisco) are finally realizing that these virtual images are super important for education and control plane testing.  While we can’t replace line-rate hardware with virtual images, we can test configurations, bring up routing protocols, test connectivity.  Of course testing Ansible Networking Playbooks is perfect for a virtual environment.  The worse thing about automation is I can automate a mistake across hundreds of nodes at the same time.  While working at Cumulus Networks we would replicate entire customer environments with virtual images and supply them to customers as Vagrantfiles.  This helped customers have a virtual playground to test and play with their automation scripts.  I think this strategy of virtual topologies should be how all network operators test their network automation strategy.  Let me elaborate on some networking vendors:

Arista

Arista has a common NOS (network operating system) amongst their hardware called EOS (Extensible Operating System).  If you create a free account on their website, they will allow you to download a virtual EOS (vEOS) for free.  Comment below if you have problems, I found this very easy.  I am pretty sure the only limitation with this free VM is the amount of ports (I think by default it is limited to 4).  What I am not sure about is if you can pay for more ports.  For the testing I was doing it worked great on my laptop.

Cisco

Cisco Systems has three main platforms that I use: Cisco IOS, Cisco NX-OS and Cisco IOS-XR.  All three of them have virtual images, but they require entitlement on you account, from what I have seen is that if you own the physical gear you automatically can get the virtual image.  I would be curious about other people’s experiences here.  Another option is using Cisco VIRL.

I wrote a Knowledge Base article for Red Hat Ansible Engine: https://access.redhat.com/articles/3199502 . This is a super simple guide on just getting Cisco NX-OSv up and running on your laptop (in my case a Macbook Pro).

Cumulus Networks

For Cumulus Linux they have a free version called Cumulus VX (for virtual experience).  You have to register, but you can download it here: https://cumulusnetworks.com/products/cumulus-vx/ Unlike Arista, there is no port limitation, so you can add as many ports as you want (depending on the underlying platform, e.g. VirtualBox vs KVM).

Another cool tool that Cumulus Networks provides for free is called topology converter. This python script creates a virtual topology (using Vagrant) from a network map (in the form of dot notation).  This allows users of Cumulus Linux (or really any Linux operating system) to build complex topologies.  While I was working at Cumulus Networks I could run well over a hundred Cumulus VX instances on a single server.  I highly encourage you to play with this tool.

Juniper

Juniper Networks has a few different virtual images floating around, including vSRX and vQFX.  My Juniper account already has entitlement to the virtual images through my employer, but they have published a Vagrant image that is not behind a login wall or paywall here: https://github.com/Juniper/vqfx10k-vagrant

VyOS

VyOS is an open source fork of Vyatta routing software.  While VyOS might be one of the networking platforms on here you have never heard of, many people use VyOS in production as a vRouter.  Their use-case is often peering to a service provider where they already have limited bandwidth out of the data center, so not having 100Gbps line-rate is not a problem.  Having Vagrant images and access to run virtual images in KVM or VirtualBox is really nice. to test out BGP configurations, prefix lists, and more.  Check out there website: https://vyos.io/

While layer 2 configuration is very different from other networking vendors, the OSPF and BGP configurations will be very similar to what you see on Cisco IOS and Cumulus, so VyOS could also be used to learn, train and pass networking certifications on those layer 3 technologies.

Summary

While I am sure many other networking platforms are out there (e.g. F5 Networks) these are some of the ones I play with the most.  I am super excited about all the virtual networks people are creating, because it means that network operators can test network changes on a virtual topology versus messing up their production network.  I am sure we will see people implement really interesting CI/CD pipelines in the future, where they can automate changes into their virtual development environment before touching any production equipment.

Infoblox Integration in Ansible 2.5

The Ansible 2.5 open source project release includes the following Infoblox Network Identity Operating System (NIOS) enablement:

  • Five modules
  • A lookup plugin (for querying Infoblox NIOS objects)
  • A dynamic inventory script

For network professionals, this means that existing networking Ansible Playbooks can utilize existing Infoblox infrastructure for IP Address Management (IPAM), using Infoblox for tracking inventory and more. For more information on Infoblox terminology, documentation and examples, refer to the Infoblox website

See the rest of the blog post over on Ansible.com:
https://www.ansible.com/blog/infoblox-integration-in-ansible-2.5

Networking Features in Ansible 2.5

The upcoming Ansible 2.5 open source project release has some really exciting improvements, and the following blog highlights just a few of the notable additions. In typical Ansible fashion, development of networking enhancements is done in the open with the help of the community. You can follow along by watching the networking GitHub project board, as well as the roadmap for Ansible 2.5 via the networking wiki page.

A few highlighted features include:

New Connection Types: network_cli and NETCONF

Ansible Fact Improvements

Improved Logging

Continued Enablement for Declarative Intent

Persistent SSH Connection Improvements

Additional Platforms and Modules

See the rest of the blog post over on Ansible.com: https://www.ansible.com/blog/coming-soon-networking-features-in-ansible-2.5

How to add line numbers to VI by default

I am running on Snow Leopard 10.6.6. at the time of this post.  VI is a handy tool to use because it is installed on every single non-windows box I have ever seen.  I originally only used nano and I have found out that nano is not everywhere.

1) you need to locate your .vimrc file, on osx I just did a locate vimrc and got this

bash-3.2# locate vimrc
/opt/local/var/macports/sources/rsync.macports.org/release/ports/editors/vim-app/files/gvimrc
/opt/local/var/macports/sources/rsync.macports.org/release/ports/editors/vim-app/files/vimrc
/usr/share/vim/vim72/gvimrc_example.vim
/usr/share/vim/vim72/vimrc_example.vim
/usr/share/vim/vimrc

2) now just vi open that file

I did a vi /usr/share/vim/vimrc and then added the line set number to the end here is how my file looks->

" Configuration file for vim 
set modelines=0         " CVE-2007-2438

" Normally we use vim-extensions. If you want true vi-compatibility
" remove change the following statements
set nocompatible        " Use Vim defaults instead of 100% vi compatibility
set backspace=2         " more powerful backspacing

" Don't write backup file if vim is being called by "crontab -e" 
au BufWrite /private/tmp/crontab.* set nowritebackup
" Don't write backup file if vim is being called by "chpass"
au BufWrite /private/etc/pw.* set nowritebackup

set number

3) now quit and save, everytime you open vi it will show line numbers, to turn them off you can do a :set nonumber

Custom Category Menu for WordPress

So here is another quick WordPress tutorial that will help deal with ‘post categories’. WordPress posts can be broken into categories so that if you have some posts marked as ‘pet related’ and some posts as ‘human related’ you could mark them as such. Usually most theme will have something like a ‘category xxx’ beneath each post so you knew what that post was related to.

Now If you want to filter your posts by category without using a widget or built-in-menu you can add your own custom menu anywhere you want. There are two important features built into the WordPress API that will help you with this. The first one is a function you could find from the wordpress api wp_list_categories and the custom css class built into wordpress current-cat (look at my css to see my implementation).

What you want to do if you want this on particular pages is to use a custom template where you use the function like I did below, or do what I did and add this code directly to your index.php file then check your URL with PHP to see if you want to display or not. In this case I only want to display on the page cavanaugh.pro/sean/news (my main blog page) and cavanaugh.pro/sean/category/”anything can be here”. I want it displayed on every category page. I used the php function substr to cut my url down to just the first 10 characters. I.E. www.cavanaugh.pro/sean/category/blahblahblah is shortened to www.cavanaugh.pro/sean/category/. The cavanaugh.pro/sean part is never used here. If you want the whole URL check my post here. Please comment below so I know how to improve this how-to.

<?php 

$sean_url=$_SERVER['REQUEST_URI'];
$sean_url=substr($sean_url, 0, 10); 
if($sean_url=='/news/')
{
 echo "<div id='custom_category_menu'>
 Categories: <u>All</u>"; 
 wp_list_categories('orderby=name&title_li=');
 echo "</div>";
}

else if ($sean_url=='/category/')
{
 echo "<div id='custom_category_menu'>
 Categories: <a href='/news/'>All</a>"; 
 wp_list_categories('orderby=name&title_li=');
 echo "</div>";
}
else
{
 //not a category or blog page
}
?>

and here is the css

#custom_category_menu{
text-transform:uppercase;
background-color:#777777;
background-image:-moz-linear-gradient(center bottom , #666666, #7F7F7F);
-moz-linear-gradient(bottom,#666,#7F7F7F);
-moz-border-radius: 4px;
-khtml-border-radius: 4px;
-webkit-border-radius: 4px;
border-radius: 4px;
padding:6px;
margin: 5px 0 5px 0;
font: 11px Arial,Verdana,sans-serif

}

#custom_category_menu li{
border-right: 1px solid #686868;
border-left: 1px solid gray;
display:inline;
list-style:none outside none;
padding:0 4px 0 4px;

}

#custom_category_menu li.current-cat a {
color:#ffffff;
text-decoration:underline;
}

How to Grab your URL with PHP

Sometimes you want to grab your url from the web browser to do some thinking (maybe I want to display flowers on a random page, or want to display a lock if https is enabled). Here is some code that I have seen used over and over, and I have taken parts of it and used it for many a web project.

<?php
function curPageURL() {
 $pageURL = 'http';
 if ($_SERVER["HTTPS"] == "on") {$pageURL .= "s";}
 $pageURL .= "://";
 if ($_SERVER["SERVER_PORT"] != "80") {
  $pageURL .= $_SERVER["SERVER_NAME"].":".$_SERVER["SERVER_PORT"].$_SERVER["REQUEST_URI"];
 } else {
  $pageURL .= $_SERVER["SERVER_NAME"].$_SERVER["REQUEST_URI"];
 }
 return $pageURL;
}
?>

now you can use the function

<?php
  echo curPageURL();
?>

wordpress menu problems with custom templates

I am assuming if you found this post you were using google!

ANYWAYS! The problem I was having on one of my sites was that the css implementation with my theme was no longer working.  Specifically I was using custom templates for certain pages and when I was on one of those pages the link to that page in the navigation menu would not be highlighted.  So usually wordpress takes care of this functionality with a css class called-> ‘.current_page_item’

A lot of times in themes you will see an implementation like this!

This would make the current page item white, so in my case when you click the ‘About’ Page you would get all your links as red except the current page, ‘About’ which would be in white.  This is awesome for user experience because not only do they see the title usually in h1 or h2 format as ‘ABOUT!’ they will see the about link formatted the way you want (in this case bright white!)

My problem was that if you use custom templates this can easily upset the normal wordpress functions.  I solved this problem by using a simple php that grabbed the address bar to see what page you were on since the function is_page(), is_home() and is_front_page() also do not work when using custom templates (not always, i see it work sometimes, but it is easier to fix it this way then dive into every theme and implementation.

When I grab the address bar I do a ‘if’ statement to check what page I am in, then throw a div tag so I can format the link appropriately.  In my case my code looks like this->

<?php if($_SERVER['REQUEST_URI']==”/2.0/blog/”) echo “<div id=’sean_override2?>”; ?>
<?php if($_SERVER['REQUEST_URI']==”/2.0/videos/”) echo “<div id=’sean_override_videos’>”; ?>
<?php wp_list_pages(‘title_li=&sort_column=menu_order&exclude=’.get_option(‘tbf2_exclude_pages’)); ?>
<?php if($_SERVER['REQUEST_URI']==”/2.0/blog/”) echo “</div>”; ?>
<?php if($_SERVER['REQUEST_URI']==”/2.0/videos/”) echo “</div>”; ?>

My css is as follows, but obviously this will be very different depending on what you are doing.

So I threw a div id tag when I was on my video page (which has id-24) so then I can over-ride any problems with the div tags and force it to white despite the is_wordpress functions failing.  YAY!  You can check out my implementation on http://www.capsoffplease.com/2.0

The video page on that page is throwing out some custom code to only grab the posts with the category tag ‘videos’ and this messed up the built in ‘current_page_item’.  My implementation does not only work awesomely, but does not slow my server down at all because it is only adding one conditional statement.  YAY!  If you found this post drop me a line, I like seeing where people come from!