Rich Martin • 00:00
Hello, everyone. Welcome to another Itential webinar. My name is Rich Martin, Director of Technical Marketing here at Itential. Today, we’re in part 3 of our ongoing series on building network automations. We are going to focus on integration and data transformation, two really important aspects of building your automation, not just with Itential, but also really if you’re going to build automations in general, these are things you have to really address and take a look at. That’s where we’re currently at today. We’ve covered some more foundational things, and we’re moving forward in our automation as we’re building an automation out. Upcoming, we are going to be talking a little bit about module automation library in our next series, and eventually finishing up with publishing and sharing automations.
Rich Martin • 00:46
For today’s demo overview, we are going to take a look at how to do an integration in our platform. We make it super easy using a specification file, ideally OpenAPI or Swagger spec, but we also support Postman collection. We’re going to target Netbox for this because they have an excellent API implementation and you’re going to probably need some source of truth in your network automation that’s usually part of the process. What we’ve done is we’ve stubbed that out and so we’re going to take a look at how we can now implement that in our automation today. Eventually, we are going to be integrating things like ServiceNow and Teams into this automation, but the process is what I want to get through to you in this session. Because the process is going to be very, very similar for anything that you want to integrate into the system and things you want to use to put into your automation. We’ll focus on Netbox, but rest assured, we will definitely get to these other ones.
Rich Martin • 01:49
as they fit into the sessions. We’re also going to use the, so once we’ve integrated Netbox, we’re going to use these API tasks for something very similar like IP address requests. Again, this is an example, you could definitely do anything that’s available to API, including querying data center infrastructure or anything like that. Big part of this is data transformation. How you take data from one API call or one API task, receive it, and format it, manipulate it. In some case, just map it straight through. You could do that too, but it occurs in a task, we call it data transformation task.
Rich Martin • 02:32
You’ll see how flexible, but also how important it is that you spend time understanding data transformation. It’s awesome because in our previous session, we did a lot of that. We did some data transformation, but we’ll spend a little more time on that today. Then eventually, as we’re iterating through this process to build, to run, to test through an area of our application called Operations Manager. With that, let me share my screen and we will continue on. Okay, so let’s start with creating an integration in our platform. With our platform under Admin Essentials, this is where a lot of the administration tasks occur or show up in our platform.
Rich Martin • 03:12
Really what we want to do is we want to take a look at a couple of things here, adapters, integrations, and integration models. We’ll start with adapters. In our platform, you can download some pre-built adapters that we have in our library. They’re freely available. In fact, we have some for NetBox. These are a form of integration that we provide to our users, and you can freely download them and use them in the platform, like I said, and they will integrate into whatever IT system or a network controller or whatever that adapter is for. And that’s very powerful and that’s very useful, but really what we want to focus in on is an integration.
Rich Martin • 03:48
So that’s a different type of way to connect to your systems. In this case, it allows you, the end user, the customer, to generate your own integration into a system on your own. So let me repeat that again. Instead of relying on a vendor like us to create an integration into a system that’s part of your ecosystem that you would like to automate across or against or with, you don’t have to wait for us to create that integration. You can generate it yourself using an API specification file that that particular vendor provides. Ideally, if they’re using something like a Swagger spec or an OpenAPI file to document their API, we can take that file in, ingest it into the system and immediately generate, or you can immediately generate an integration and start using that today.
Rich Martin • 04:43
That’s incredibly valuable and incredibly flexible for you, and it’s quite honestly a lot different from probably what you’re used to. That’s what I want to show you today. The first step of that is I can import that particular file and create an integration model. The integration model is built based off of, like I said, a specification file. One of the things I’ve pulled down is a NetBox 3.3, OpenAPI specification file. It’s a JSON format. It’s freely available.
Rich Martin • 05:14
If you’ve already running NetBox, you can access it through their API documentation in your installation. If you do a couple of Google searches, you’ll find it. We’re seeing more and more providers providing OpenAPI documentation or Swagger spec in a JSON format. Once you have that, literally, I just dropped it into here. If I validate, we can just ensure, because it’s in a JSON format, where this import wizard is going to validate that. At the very least, the integration model is a valid JSON. With that, I just click Import.
Rich Martin • 05:49
Now it’s going to go and create an integration model for me. With that, inside of that JSON file, that API documentation, it defines all of the API endpoints that are published in this particular API file. Now, here’s the great thing. This is NetBox API 3.3. They probably have a later version. This allows you to go and grab that later version. Maybe you want to set that up.
Rich Martin • 06:17
If you’re looking at it, you can set up your lab and you can even create another integration to the later version of this application and run them both concurrently. I’ll show you what that looks like in a moment. But just for the case of example here, this is what we’ve done. The first step is to create the integration model. This gives us the ability now to take a look at the way the API is laid out. It’s going to be different per vendor. They’re going to have different things, but Netbox does a great job.
Rich Martin • 06:43
You get to see pretty quickly how they’ve categorized the different features and functions and laid that into their API files or their API endpoints. So, and this is helpful. I would recommend if you’re going to get into automation is to learn to read these kind of the API documentations and also how to use the application if possible so that you can kind of see how all of this fits together. So, in our example today, really, we want to request an IP address. That would probably fall under IP address management here and it actually does. But this allows you to now from here, just in this first step, to see what’s all being published and how they’ve categorized it. So, if I wanted to do something and like query some sort of part of the inventory, it would probably be under data center DCIM, data center inventory management or infrastructure management.
Rich Martin • 07:35
And so, I can click into that and take a look at these files. So, you could, or these endpoints. So, you could take a, you know, you could take some time and investigate the API documentation. So, if I go with the IPAM, let’s take a closer look at this. So, because now you can kind of see. how the URL endpoints are laid out, gives you some idea of the organization. You see get, post, put, patch, delete.
Rich Martin • 07:56
These things will all be covered in their actual API online documentation. You can see how all of this is laid out and what their expectation of values are. But it also gives you an idea of what you can automate even at this first step, because all of these are going to be available inside of all these API endpoint calls are going to be available inside of the Automation Studio Canvas, so that you can start to utilize these. What we’re looking for is IP address. how do we get a new IP and I’ll give it a shortcut. It’s really going to be under IPAM prefixes, ID, available IPs in the post call is what allows us to request an IP and even set up some variables so that we can identify it, maybe set a description and a status. That’s what we want to do.
Rich Martin • 08:44
If I click this down arrow, you’ll see that from that API spec file that we just imported, it’s defining the values that are required here for this particular call to run. We have an ID and then a request body. Because this is all laid out inside of that, this is what you’ll start to see inside when we start to automate this and we pull the task that’s associated with this inside of the canvas. You’ll see that these fields are what are represented, and this is all coming from that spec file. This is why this is so powerful, is it allows you to go in here and based off of the ecosystem you have, and the fact that hopefully a vendor has published this to go and quickly do an integration. This is a model. If I click here on integration, now I can instantiate a version of this and it’s for test.
Rich Martin • 09:38
Give it a name. I selected the integration model that we’ve created. If I just save it, it’s now, we’ve created integration model and now an instantiation. From here, all I would need to do is fill this out to the right protocol host port depending on how it’s deployed on your network and then your authentication information, and now the system would have access to those API endpoints. This allows us to basically act like a super user. As I’m building automations, I’m just leveraging the APIs that are available, which are usually also tied to the front-end management for that application too. We’ll take a look at that in a minute, but that’s really the gist of it.
Rich Martin • 10:22
That quickly you can generate an integration model and an integration and bring all of these different systems in your environment, integrate it into the automation platform. Now you can start leveraging those APIs to automate, not just network tasks, but all of the tasks that are part of the process that support it before you even make the network. In this case, it’s gathering data, grabbing IP addresses, things like that, querying for inventory. Okay, so now let’s transition over to Automation Studio. This is where you actually build automations. And if this looks familiar, that means you paid attention to our previous episode where we’ve built this out. And so I just wanna go through it.
Rich Martin • 11:09
So what we’ve been doing just as a process now is we started off with a little bit of code. Using these stub tasks, they’re just placeholders. It helps us to whiteboard it, if you will, what all the different steps are as we’re building an automation. In this case, we’re making a network change to a CLI-driven device, a Cisco router. We put some pre-checks and post-checks in, we did some evaluations. That’s awesome. Now, we’re asking the question, in order to make a network change, or in this case, I’m bringing up a new interface, a lot of times you need a unique IP address, right? I need to gather data from some source, and that’s what we’re gonna take a look at today.
Rich Martin • 11:47
We’re gonna take a look at this step right here, querying inventory. I need, what is the inventory of IP addresses for this? And how do I access it? And then how do I leverage that API call into Netbox so that I can pass it on so that it ends up here as part of a set of configuration changes that I’m gonna push to a network device? So this is what we’ll focus on here. We’ll return to that in a moment. But for now, I’m gonna go back to this tab where we can go back into Automation Studio, and now we can create a new workflow.
Rich Martin • 12:22
And so this is the first step in kind of building that out. I would probably go ahead and create a net new automation here. I’m gonna give it the name. I’m gonna create a workflow. I’m gonna give it the name Builder Workflow 3 Netbox. Then of course, we get our start and end, and then our task list here. Now, remember a moment ago, we went back into when we onboarded the NetBox integration.
Rich Martin • 12:52
We had access to all those API calls, and the one I wanted to point out was how to grab an IP address. Again, you probably need to spend some time looking at API documentation just to understand, like I said, the format, how it’s laid out. There’s a logical format for these. But just to save some time, that particular task that I pointed out was a post, and it was IPAM prefixes ID available IPs. I know that’s a mouthful, but if I go down here to, well, let’s just go down to NetBox, this is our task palette. As we onboard different systems, whether they’re network systems or IT systems, whatever it may be, all of those API endpoints become available through here.
Rich Martin • 13:43
Under NetBox, this is all the things we looked at in the API documentation we integrated. This becomes useful here. This is already an existing one because it’s tied into our lab system but the API calls are all there. What we want to do is we want to find the API call that correlates to requesting an IP address, not just asking or getting or querying for an IP address, but actually requesting for it. It was that post version of the IPAM prefixes ID available IPs. If I go post IPAM prefixes, You’ll see that we have a couple here.
Rich Martin • 14:25
If I hover over this, I want the one that says available IPs at the end. Yeah, this is the one. They’re slightly different. You’ll notice when I did a hover, you’ll see some documentation that comes again from the spec file. I’m going to drag that here. I’m going to make this small. Since we’re just testing this step, we just want to test to make sure it works the way we want it to work. Before I merge it into the bigger workflow, it’s always good to test these individual elements and understand how they work. That first part was looking at the API documentation.
Rich Martin • 14:58
Remember, it had some required variables. I’ll zoom into this a little bit. Now that I’ve dropped that into here, build my transitions, just like that. And when I double click on this task or any task for that matter, you’ll see the variables that are required for it to run, or at least that it’s requesting and ideally run and run successfully to execute that task. Remember when we looked from the API documentation, when we first imported it and created an integration model, there was an ID, gives us a little description here, a unique integer value identifying this prefix. And then there’s a data object here.
Rich Martin • 15:37
So where does this information come from? Well, if I put the number 32 in here, that like, how did you pull that out of the air? Well, let me show you. And this is why it’s so valuable to understand if possible, to understand how this particular system works. So you can correlate the API call to how this is actually being done inside the system, maybe where this data comes from inside the actual system, like the console or the dashboard. So let me show you. So I’m specifying value 32 for this ID.
Rich Martin • 16:08
And where that comes from is here’s the net box that I’m going to be integrating into. And I’ve gone under prefixes here just to list all of the prefixes. So in this case, I want to make sure that the IP address assigned is assigned in a certain prefix because maybe this is a part of the data center and this is what’s being used. So just for testing purposes, we’ve set this up in the past. So I’m going to use this particular prefix here. So I want to assign an IP address from this prefix, 10.48.132. and click under IP addresses, we can see what’s already been assigned.
Rich Martin • 16:43
We should get the next one, assuming we get the next one here, when it’s served through the API call, so it should be 11. But note up here, IPAM prefixes, and we get the number 32. This is the unique internal to NetBox prefix ID that is assigned to this one. If I wanted to select a different prefix, I would go to that and I would navigate to that, and I’d find that prefix too. There are other ways to find it, but if you’ve got access to the dashboard, this is probably the easiest way, because you can say, okay, yes, this is the prefix that is assigned to this particular part of the network, and this is the right prefix to use. So I would use 32 here, that’s where that comes from. So that’s why I put that here.
Rich Martin • 17:21
Now, let me paste this data object in, and now this is where you would spend a little more time trying to understand what is acceptable to pass to this API call. Here, I’m filling this in. Notice, so notice this was a number, this is the required type. We talked about types last time. So I gave it a value of 32, because it’s a number, we are only going to accept numbers here. We want to make sure it’s a number, and we can go up and down from there, or you can type it in directly. 32 is here.
Rich Martin • 17:53
In this case, data is required, and it’s an object. So when it’s an object, it’s going to be expressed as a JSON object. JSON object is identified with the curly braces open and closed. And in this case, I’m putting in some values here. Status is active. Remember our keys and our values. So the key status, the value active, the key description, and then webinar build a workflow test.
Rich Martin • 18:17
I’ve, where did I find that from? Well, that came again, this is where it helps to spend some time in the API documentation that Netbox publishes, and they’ll describe these fields and what’s valid for them. And they have to, and again, they expect it in an object. So we’re gonna pass it in as a JSON object. And I’m statically doing this here, but it can also be done dynamically, but since we’re testing, and in this case, how are we gonna use this status is okay. I mean, static is okay, but in the future, if we’re gonna do something else with this, maybe this becomes modular. Maybe this, we pass these values, or maybe the entire object in from a transformation or from some other source, and we can certainly do that.
Rich Martin • 18:57
But for testing, it’s easier to do it static until we understand how everything works. So where does that come from? Again, API documentation, but to give you a clue, and this isn’t always the case, but to give you a clue, if I go back to the IP addresses, remember, this is going to request a new IP. So when I’m requesting an IP from this particular prefix 32, You also see some statuses that can be set here. And in this case, description and status, role tenant assigned. So that already gives me some hints that for the post, at least, because it’s requesting an object, it’s allowing me to set something.
Rich Martin • 19:30
And in this case, it’s allowing me to set the status as active and the description with the text blurb that I want to set it to. So that’s what’s there. You can’t always make that assumption. You really need to read the API documentation just to ensure because it’ll specify from that vendor’s documentation what they expect those fields to look like, what are acceptable and not acceptable. But in this case, again, it gives you some hints as to, oh, okay, this is how I can set this, or this is available for me to set. So that’s where that comes from. And I always like to cover that so we don’t just pull things out of the air.
Rich Martin • 20:03
So with that being said, that should be good. Now, if I save this, and remember for testing purposes, running from here is kind of helpful. Oh, actually, there is one more thing because I mentioned earlier before I run it. that we can support multiple versions of your IT systems as integrations and adapters. If I click on this again, this is an API call to a NetBox instance, but if I have multiple, which one? In this case, I actually want to go under Advanced. I double-click this task, I go to Advanced.
Rich Martin • 20:36
If I go to Task Options, if there are multiple integrations or adapters, I can select those different systems. I can have a production system, and a lab system, and a dev system, and we can now select it there. Now I’ve pointed it to the right version because we can have multiple of those on here, so you can build automations across those. Again, great to dev or test and then move to production. Now if we save it, and I run. Let’s take a look at what this looks like.
Rich Martin • 21:08
Now we’re in Operations Manager looking at the job itself. You’ve noticed here that it’s already finished. It’s got this. If I double-click this, so this instantiates the automation and it’s one step, but again, we’re testing. It instantiates it and runs it and executes it. When I double-click this, I see the variables that are incoming. These are the variables that were fed into this API task or this API endpoint call to NetBox.
Rich Martin • 21:35
This is what we statically assigned when we double-click that variable in the Automation Studio, this ID, and then this data object active in this description. We did that. That means that that’s the data it used to make the API call into NetBox. If I click here, this is the outgoing. This is all the data that NetBox has returned subsequent to the API call, and there’s a ton of data in here. That’s the point. There’s a lot of data in here, and not all of it may be relevant to what we want to use in our automation. In fact, At least for what we want to do, most of it is not relevant.
Rich Martin • 22:10
The most relevant is this field right here, the address that was returned. You’ll notice 10.48.132.11 slash 24, that’s the address that was returned to us. If I click over back to the NetBox dashboard and if I reload this, this is exactly what happened. That test was successful, I made the successful call in. Not only did it respond back with the next IP here, but it also accepted our object that set the status as active and the description as webinar build workflow test. This gives you an idea, this is how we can iterate. If I wanted to do a query into the datacenter management side of NetBox, you would find that particular task, drag it in.
Rich Martin • 22:55
Let’s take a look at the variables, understand what they relate to, maybe look at the API documentation, maybe look at the application itself, the NetBox console or dashboard of the system, and then start to understand how all of this fits together and ties together. With that, if I go back to here, now we can take this, and remember, this data is being fed back to us as a result from a successful call into the NetBox. It’s got the data we want along with a lot of data that we don’t necessarily need. If I’m going to utilize this IP address to make a change in the network, I need to modify this data in some way so it’s acceptable to the API task that will actually make the network change. In this case, if it’s a CLI command, that certainly doesn’t look like a CLI command that would be acceptable or usable on a Cisco device. We have to do something with this device or with this data, specifically this piece of it, and that’s what the data transformation is all about.
Rich Martin • 24:00
This is what’s so useful. If I go to here, these three buttons, I can copy this whole object here. That’s what I want to do. I want to copy the whole object because now we’re going to work on our data transformation. Because everything around our platform is JSON objects, JSON schemas, things like that, I want to copy this because this is going to be the input for our data transformation. The output of a successful call should be the input of our transformation so that we can extract this, manipulate it any way we want so that it’s usable in a subsequent call in our automation. That’s what we’ll do next. So let me go over to this tab here.
Rich Martin • 24:42
We’ll keep that one in the background for now. And if I go back into Automation Studio, this is also where we would build the transformation. So I can create here, instead of a new workflow, I’m going to create a transformation. We’ll give it the name, basically the same name, because it’s a transformation and not a workflow itself, but at least it already exists. Name it two. So now you’ll see that we have an incoming schema and an outgoing schema. Let me reload this and see if I can get that.
Rich Martin • 25:22
There we go. Now this is our data transformation canvas. It looks similar to the automation canvas, but we’re not building an automation, we’re building a transformation here. We will use this transformation in the workflow in a moment, but we’ll build it and test it from here first. So what we want to do is first create an incoming schema. Every transformation is going to have at least one incoming schema and at least one outgoing schema. However, you could have multiple incoming schemas and multiple outgoing schemas.
Rich Martin • 25:53
That’s perfectly okay. And in some cases, that’s exactly what you would want. In some cases, maybe not. You have that flexibility. So we can create an incoming schema. So this is gonna be a JSON schema that defines the data format that the transformation should expect to get, right? And this is also a form of data validation.
Rich Martin • 26:13
If it doesn’t fit this format, then the transformation says this doesn’t match up and it’s not gonna run. So the best way to ensure that we create the right schema is to infer it from an actual API call. And that’s exactly what we did here. When I copy this, this is the output from an actual API call. We wanna use that as the input here. So if I paste that into the right side, this is the JSON object, the payload that came from that. But if I click infer schema, this is going to turn it back into a JSON schema that defines exactly what we should expect to get data-wise.
Rich Martin • 26:51
And then the cool thing about this is it also preserves any of the values because they become examples. And this is great for testing. So I can call this from netbox. This is data from netbox. So I’m just gonna give it a unique name. And now you’ll see that all of the framework of that data has now appeared here on the left side in the incoming schema. And remember what we really wanted, if I go back to our job that’s finished and run, is I want this value here from this key address and it appears right here at the top under result.
Rich Martin • 27:31
If I go up here and I go into result and I follow this down, you’ll see I get to address here, and we can see it’s defined as a string. I could take that now, and just as an example, I can click on outgoing schema, and it’s going to infer based off of the fact that it’s string, I don’t actually have to fill anything out. If I want to do some direct mapping, if that address string is in the exact format I need it in, I can just map it directly over. I don’t have to do any data manipulation. So I could save this and we could run it. It’s going to show me, so what I’ve done, I haven’t run an automation, this is a testing feature inside data transformation. Because data transformation is incredibly important, even in our platform, but even if you’re writing code, you’re going to take data from an API call and you’re going to manipulate it in some way so that it fits a subsequent API call or some other format that’s required for that data.
Rich Martin • 28:31
It’s the same idea except we’re taking that concept and making it visual, so it’s easier to map and understand. In this case, what we’ve done is we’ve just taken this as it would appear coming from the API call and mapping it over. If a subsequent API call that we used, that we needed an IP address for, required it in this particular format and that exact format, we could take that variable and map it straight over. Remember, this is going to be a task, so when data transformation receives the data from the NetBox API call, in this case, it’s going to extract just the address and make that available to another task as a variable it can use as well. But a lot of times you’ll see that that could be useful sometimes, and a lot of times you’re going to have to make changes to something. And so I always think about two questions. What data do I want?
Rich Martin • 29:25
We answered that here by looking at the output from this call. This is the data that I want. Then when I created the schema, I identified it here, this is the data that I want. But then I have to ask the question, how am I going to use that data? In this case, I want to use that data as a CLI command. Now, that data could also be part of a payload, a JSON payload for another API call. If you’re talking to a network controller to make a change, this would be a little different looking.
Rich Martin • 29:55
But for the sake of as an example, let’s format that as a CLI call. A CLI command so that we can configure an IP address on this interface, and then add that to the list of commands that we push to a particular device. So we can’t use it here, especially if it’s a Cisco iOS device. We need to have this change. We need to have the core of it, the IP address, but we need to have some changes made to this. So in order to do that, we need to do some manipulation, some transformation. And so if I click here, this gives us access to all of these methods.
Rich Martin • 30:33
Now, don’t get overwhelmed by all these methods. A lot of them you’re gonna use over and over and over again, and you can always access documentation to understand what these methods are. I’m gonna delete this for a moment. We kind of already see what that’s about, but let’s make some methods and some modifications to this. So the first thing is, if we want to extract just this part of it from the string, we really need to separate this somehow from the rest of it. And that’s where these methods come into place. So since we’re operating on a string, right?
Rich Martin • 31:10
The address is defined as a string, that’s its type. Then a lot of the operations that we, the methods we want to use may come from here. And in this case, we, one of the things that is really useful is something called split. Now there’s a different, there’s several ways you could do this. And as you start to become familiar with these different methods, you’ll start to understand which ones work well in certain situations, and which ones work well in other situations. The split is nice because you can take a larger string and split it up based off of a character. And so since the Netbox API call is always going to return something that looks like this, with a slash, it’s going to give us the slider notation, and it’s going to have a slash in front of it.
Rich Martin • 31:51
We can do a split and split the string into two different strings. based off of that character right there, the forward slash. And so to do that, I would just drag this into the canvas. And it’s going to give you some parameters. Very similar to a task, I guess you could think of it in that terms. Instead of double-clicking a task and seeing the parameters of the values of the variables it needs, when you drag a task, a method, onto the canvas, it’s going to give you all the required or optional values here, too. So at this point, it’s just a matter of mapping.
Rich Martin • 32:25
So string can map to another string here. That’s valid. It’s not going to allow you to map it to something else that’s not a string, or it’s not acceptable type. So that’s our first parameter. And by the way, on any of these, you can hover over here to get some basic documentation. Or if you click on it, we won’t do it. But if you click on it, you’ll get to a lot more deeper documentation on how this particular method is used.
Rich Martin • 32:48
So in this case, we take the string. So this is the full string. And now we need the separator. So it was the separator, that forward slash. So if I do the forward slash and the limit, we’re not going to use here and notice it’s not required. But you’ll also see that this returns an array. Now, an array is different from a string.
Rich Martin • 33:07
We talked about that type last time. An array is a series of elements. In this case, it’s going to be an array of strings. But let’s take a look at what this looks like. So we did a direct map to address. We saw what it natively looked like coming from that box in our example. So if I click over here and add this, it’s going to say ID, say IP address.
Rich Martin • 33:37
Guess I could have kept it the same. Array, save. Now I can map it over to here. Now I’ll save it, and if we run our test again, now we can take a look at our array output. This is showing the final output of our outgoing schema, if this were to run using that example data. You’ll see this split method now has successfully split that string into two different. strings as part of an array.
Rich Martin • 34:07
So now we’ve got this forward, the first portion here, which is element 0, and then the second portion, which is the CIDR mask of value for the net mask, which is 24. Now, we don’t need 24 for this, but you might need 24 in some other use case. We don’t necessarily need it for this. So we’re just going to take this. Now, if I were going to turn this into a Cisco CLI command to configure an interface, then I certainly will need to add a little more to it. But the first action here is it’s an array, and I really need it as a string. And we know it’s an array.
Rich Martin • 34:40
Remember, of our last session, the array has the square brackets open and close. So how do we access that? So now we get to go up here and use this method called getIndex. So this returns, in this case, a string at the value. So we feed it an array, and then we tell it the index number or the element number that we want to output. And then it will output it, in this case, as a string, because it is a string. So if I click off of that, delete it, and now give the parameter array here to getIndex and give it index 0, because that’s the first value that we want.
Rich Martin • 35:18
Now what I want to do is I want to edit this, and instead of the type array, I’m just going to give it string. I’m going to change the type so that we can match what’s going to come out of this because it’s going to give us a string instead of an array now. I’ll save it, we’ll test it, we’ll run it, and as you can see here, that’s exactly what we’ve got. We’ve gotten the IP address that we need. We’ve done some transformation. It came in as a IP address slash 24. We’ve broken the first part of it out, just the IP address.
Rich Martin • 35:52
We’ve extracted it from the array, now it’s a string. Now if I want to turn it into a CLI command, I have to do something. I have to surround it by interface, or I’m sorry, IP space address, space the IP, and then the net mask. In this case, since it’s a loopback, I’m going to do 255.255.255.255. There’s a couple of ways you could do this. One of those ways is you could use some of these other string methods that are available. But really flexible way to do it, that’s basically a single step is using a template literal.
Rich Martin • 36:30
This allows us to create a custom template. and embed certain variables. We can pass variables into it, and we can embed text before and after it. And it makes it perfect for CLI commands or formatting messages for like Slack or ServiceNow, or if you need to format something for HTML, it allows you to have that kind of flexibility. So when I drag that on here, there’s not a whole lot going on until I click this button. And when I click that button, I’m given basically a free form access here. And so what you do is you type in the text you want, and in this case, I’m going to format it as a CLI command.
Rich Martin • 37:09
that you would type in because we want to push that to an iOS device. So this is the command you would type in from the command line. However, I’m embedding a variable here, and your variables are going to start with a dollar sign, and then the curly and closed brackets along with a name. That name just has to be unique to the template literal. So these are static IP space address space, and then the IP address that we want to use in this template is a variable. And then this part here, which is the net mask and dotted quad is static as well. Now, when I click update, this particular method, the template literal now understands the variable that we assigned as IP, gives it that name.
Rich Martin • 37:52
And so now what I can do is I can feed it into here. So now the actual IP address that we extracted through these first two steps is going to be input into this template. It’s going to be replaced here with the actual IP trust that we got in the right format, and then it should output that as a string. And instead of calling an IP address this time, let’s change the name. Let’s call it iOS command. Now, if we save that and then run this test again, there we go. So we’ve taken the address string and we’ve turned it into a proper CLI-formatted command for a Cisco iOS device that now can be pushed.
Rich Martin • 38:40
And so this is just the data transformation. We’ve just been testing. This isn’t an actual automation. But this gives us the framework to manipulate the data and change it into the format that’s acceptable for an iOS command. So that’s what I mean by, where does the data come from, what is the data that I want, and how am I going to use that data? I’m going to use that data in a format that’s a CLI command. If I was talking to a network controller, right?
Rich Martin • 39:10
I might have to, I would not might, I would definitely need to build another data payload. It may be a JSON object, right? I could use the template literal there for that as well. I could create what looks like a JSON object, save that and output that as a JSON object that could be passed to that network controller API call in my automation. And so this is why this is so important because between two different systems, the data is not gonna be in the right format most likely. And so you’re gonna have to do something to make that data in the right format. And the cool thing is these are reusable.
Rich Martin • 39:46
So anytime I’m doing a likewise function, I’m pulling something, pulling an IP address from NetBox and I need to configure it for a CLI command, this could be used, right? So we can actually use this as a reusable modular asset. So if I click save there, we’ve completed our data transformation. And now let’s go back to our automation. And so we can now attach that into our workflow here. So to do that, I can just type in transformation. This is going to pull up the transformation task, which is part of our platform.
Rich Martin • 40:26
And if I drop it on here, it’ll attach itself. And now I can click on this, and it’s going to ask me for the transformation. We gave it build a workflow 3. Didn’t we call it build a workflow 3? Yeah, I think so. Build a workflow 3 netbox 2. That’s the one.
Rich Martin • 40:50
OK, so when I click on that, it’s saying, OK, here’s the variable that you need to define. Now, where did that come from? From netbox. If I click over here real quick, remember when we created our incoming schema? I called it from netbox, and I pasted in the output from the operations manager call as our live data that we want to use as an example, and we inferred the schema. That’s what it’s asking for. So it understands, now that that transformation has been defined, it understands this is what’s required because we defined that.
Rich Martin • 41:24
Now, where does the data come from? In this case, it needs to come from the task before it. The output of this should be the input of this, and then this should output the correct CLI command for us. That’s the way we’ve done it. If I go to task here, instead of statically assigning it, I go to task here. What I really should have done was I really should have renamed this task because it’s pulling the name from here. But we’ll just leave it here. But that’s the correct task, because it’s the only task that’s in here that can be selected.
Rich Martin • 41:54
I’ll keep it here, I’ll click that, and I’ll double-click this and we’ll just say, Fit IP address. That makes it a nice cleaner. So now the previous task is named get IP address from that box. That makes it easier to understand the previous tasks and the output. So again, that previous tasks output now becomes the input for here. And then on the output side, this is the iOS command that we’ve set. There’s always an error that can be set to for every task if there’s an error in running the command or running the API task.
Rich Martin • 42:35
But in this case, this is what we’ve defined in our data transformation. So this is what we should expect as output. Okay, and with that, we have finished adding the transformation and now we can test it and run it to see it all working together. So if I click run here, and we go into the job manager, you’ll see that the first task, which was the API call to Netbox completed, we could double click that and we can take a look at the variables, most importantly, the outgoing variables. We know what we fed to it. Now we need to see what came out of it. And of course, now we’re seeing an IP address here that was given to us.
Rich Martin • 43:12
And now the key piece of this that we just added is the transformation. So if I double click on that, let’s take a look at the incoming. So remember the outgoing with this is set up to be the incoming of this. That’s what we set up in the transformation task. So you can see the incoming variable map here, that object came from the Netbox call. That’s what we mapped in the workflow task just a moment ago. And then if I click outgoing, so this is the output of the transformation task.
Rich Martin • 43:39
So this is the transformation we built and it’s putting it into the right format. And indeed it has the same IP address as what we received from the NetBox API call. So that’s a good example of how to test and work different, do an integration, how to identify the API task that you’re looking for, how to leverage API documentation, both in our system and of course, external to it from the vendor. And then also how to take a look at the application itself, the dashboard or console that you log into and determine how this all maps and works together. So with that, now we can turn our attention to the following. We can go back to our overall workflow here. And what we’ve normally been doing, let me zoom in a bit so we can take a look.
Rich Martin • 44:30
What we’ve normally been doing is as we’ve created these stub tasks, when we first started this series, we’ve been slowly replacing them with working tasks. So we could do that same thing here. So if I remove this, I can delete and merge this. Let me… Give it some more room. If I open my task palette, recall that the task that we were just been testing is post-iPan prefixes available IP, so that’s what we’ve been doing. I can drag that onto the canvas here and drop it in, give it a little room there, and then the second task we could have is a transformation.
Rich Martin • 45:14
We can drop that in. Then by double-clicking, we could start filling out these variables. It’s like we did in our testing procedure a moment ago. And then we continue to do that for the transformation. But I want to pause here, because every good series has a cliffhanger. And the cliffhanger is this. If you think about what we just did, we could merge this back into our primary workflow, replace that one sub-task with these two tasks that we’ve just been testing across.
Rich Martin • 45:52
But I want you to think about what we’ve done. We’ve created a standalone. It’s two tasks right now, but a standalone function, if you will, that could be usable. in many different environments. Anytime you need an IP address, this simple two-step task, and maybe we can flush it out a little bit, but the simple set of tasks can be an independent workflow. Maybe we need to tweak it a little bit. Maybe instead of statically defining some of the input variables, maybe we create variables that we pass into that.
Rich Martin • 46:22
But the idea here is thinking in terms of modularity. This being able to query and get an IP address from a system, or open a ticket, or send a message to a Slack channel, or a Teams channel. All of these things are going to be done quite often in all kinds of different automations, and as part of a process. And so now you should start thinking about how we can modularize some of these things so we don’t have to go back and recreate all of this. So literally, I’m going back and recreating these steps in a larger workflow. Instead of that, so instead of merging that in like we have been doing, this is a great opportunity to now start to take a look at this and say, this should be a modular task. Maybe we tweak this a little bit.
Rich Martin • 47:04
We go through our testing procedures, we tweak it a little bit, but then we turn it into a standalone workflow that can be run as a child job from within larger workflows. And that is our cliffhanger. We won’t merge this into this until our next episode. And when we do that episode, the focus of that is creating your own modular library, which fits right into this. So in that episode, we will definitely take this, we’ll flush it out a little bit, we’ll turn it into a child job that’s standalone that can now be leveraged not only in this workflow, but many others. And then we will also show you how to leverage some of the modular libraries that you may also create for other systems or may come from our pre-built library as well, and how you can leverage those. And then we’ll end up finishing out the episode.
Rich Martin • 47:55
automation that we’ve been working on in this series. Stay tuned, that’s your cliffhanger. We will merge it in, but we’re going to show you a different way to now merge these changes into this workflow that leverages modularity. I think that’s something that every network engineer and every network engineer that’s working in automation should start thinking about modularity in the sense of, we’ve done it once, this is a repeatable task, let’s leverage it so people don’t have to go through and recreate all of this again. And that way we make building automations even more efficient with our time. And with that, that would conclude our webinar for today. I want to say thank you so much, and again, we look forward to having you on with the next webinar, and where we start to finish this out.
Rich Martin • 48:48
We’ve rounded the corner, and we’re going to finish this out and complete this in the next two episodes of the series. Thank you very much, and I hope you have a great day, great afternoon, or great evening. Bye-bye.