Using Variable Modifiers with CLI Templates

In a previous blog post, the ability to leverage CLI scripts with variables was explained. This served as an introduction to the feature but did not cover all of the capabilities. For example, in the previous blog, the example of configuring the IP address of a FortiGate interface and DHCP settings for that interface required three separate variables to be defined. However, there is a way to accomplish the same task with just one variable.

Meta Field (Variable) modifiers

The CLI Template script variables can accept modifiers to do light text transformations to the value defined under each FortiGate. From testing, it seems like this functionality can primarily be useful for variables that are in a dotted decimal IP address format. An example of this format would be the following:

192.168.100.1

Assuming that this value is assigned to a meta field (variable) called $subnet1_fgt_ip, its individual numbers delimited by the “.” can be referenced into their own field. For example:

IP Address PositionValue
1192
2168
3100
41

These individual fields can be referenced and modified through the use of the following syntax:

$(<meta field name>:<position>,<modifier>)

Position

The position referenced above refers to the IP address position as listed in the table above. In the case of a standard IPv4 address, there are a total of four positions and are referred to as 1, 2, 3, or 4 in the syntax.

Modifier

The modifier referenced above can refer to an addition or subtraction mathematical function or just setting the position to to a specific number. Here are the two examples of this in use:

Mathematical Function

Assuming that the meta field (variable) $subnet1_fgt_ip is set to the value “192.168.100.1”. You can use the following modifier:

$(subnet1_fgt_ip:1,+1:2,-1:3,+5:4,+10)

The resultant of the execution of this variable within a CLI Template script is the following value:

193.167.105.11

Please note that if you do not use a math operator (such as addition or subtraction), the FortiManager will just substitute the value of that positioni with the number defined in the modifier.

This does not prove to be very useful in this form, however a more practical example is to use a single variable to set the FortiGate IP address, DHCP scope start and DHCP scope end. This consolidation allows for an improved efficiency of FortiGate deployment.

Single Variable with Modifiers

A common deployment scenario with distributed FortiGates is to define a interface specific IP address and DHCP scope. This usually results in three site specific settings:

IP address of FortiGate

DHCP Start IP

DHCP End IP

Normally this would require defining three separate variables, however, with the use of variable modifiers, this can be accomplished with one variable. See below for the corresponding CLI Template snippet:

config system interface
    edit "internal"
        set vdom "root"
        set ip $(subnet1_fgt_ip) 255.255.255.0 #1
        set allowaccess ping https ssh http fgfm capwap
        set type hard-switch
        set stp enable
        set role lan
    next
end
config system dhcp server
    edit 1
        set dns-service default
        set default-gateway $(subnet1_fgt_ip) #2
        set netmask 255.255.255.0
        set interface "internal"
        config ip-range
            edit 1
                set start-ip $(subnet1_fgt_ip:4,150) #3
                set end-ip $(subnet1_fgt_ip:4,200) #4
            next
        end
    next
end

See the following explanation to this script:

set ip $(subnet1_fgt_ip) 255.255.255.0

1. Sets the IP address of the “internal” interface to “192.168.100.1”

set default-gateway $(subnet1_fgt_ip)

2. Sets the DHCP scope’s “default gateway” for the “internal” interface to “192.168.100.1”

set start-ip $(subnet1_fgt_ip:4,150)

3. Sets the DHCP scope’s starting IP address to “192.168.100.150”

set end-ip $(subnet1_fgt_ip:4,200)

4. Sets the DHCP scope’s starting IP address to “192.168.100.200”

Here’s a walk through of all of these steps completed in the FortiManager and the resultant. This will not contain all of the details as they were covered in previous blog articles.

1. Identify the FortiGates to apply the CLI Template script

2. Set the corresponding meta fields for each FortiGate

Setting the variable “subnet1_fgt_ip” to value “10.10.1.1” for “office1”
Setting the variable “subnet1_fgt_ip” to value “10.20.1.1” for “office2”

3. Create the script referencing these variables to apply to the FortiGates

4. Assign the CLI Template to all applicable FortiGates

5. Apply the configuration to each FortiGate

6. Validate the configurations on each FortiGate

5 1 vote
Article Rating
Subscribe
Notify of
guest
6 Comments
Oldest
Newest Most Voted
Inline Feedbacks
View all comments
hoosee

Hi!

Do you have any good tips on how to deploy changes created by an external script?

Currently I have a script what creates a config which I can copy & paste directly to a Fortigate and it creates interfaces, SD-WAN, IPSec, BGP, switch & AP -config. The only way I can get this in via FortiManager is to use direct CLI -method. Is this the only way to go?

hoosee

I was thinking about a combination of options 1&3.

Populating those meta fields by hand is a pain in the butt and FortiManager functions don’t provide enough flexibility compared to python scripts. However I was thinking that instead of generating direct configuration with python, I could just use it to create a new device with those meta fields over the API and then let FMG take care of the rest.

Thank you for the input! Also reading your articles gave me a lot of valuable insight about the possibilities and the restrictions ZTP with Fortinet. I’ll keep you posted! 🙂

hoosee

Hi! After holidays and other work stuff, it’s time to get back to the topic! Currently I have two ways of generating the ZTP-config: 1) Create ‘model device’ and populate it’s meta-fields by using Ansible This is pretty straightforward and I would pretty much suggest using this method if your configuration is simple and uniform. I’m also able to assign policy packages, system templates etc. via Ansible so this is really simple. Just provide Ansible with all data required (how to connect to FMG, device data such as serial number, subnets…) and it will take care of everything. 2) Create… Read more »