77#
88# Firewall admin with superuser and IP address is required.
99#
10- # REQURED :
10+ # REQUIRED :
1111# export PANOS_HOST=""
1212# export PANOS_USER="" #User *MUST* have Commit and Import Permissions in XML API for Admin Role
1313# export PANOS_PASS=""
1414#
1515# OPTIONAL
16- # export PANOS_TEMPLATE="" #Template Name of panorama managed devices
16+ # export PANOS_TEMPLATE="" # Template Name of panorama managed devices
17+ # export PANOS_TEMPLATE_STACK="" # set a Template Stack if certificate should also be pushed automatically
18+ # export PANOS_VSYS="Shared" # name of the vsys to import the certificate
1719#
1820# The script will automatically generate a new API key if
1921# no key is found, or if a saved key has expired or is invalid.
2022
23+ _COMMIT_WAIT_INTERVAL=30 # query commit status every 30 seconds
24+ _COMMIT_WAIT_ITERATIONS=20 # query commit status 20 times (20*30 = 600 seconds = 10 minutes)
25+
2126# This function is to parse the XML response from the firewall
2227parse_response () {
2328 type=$2
29+ _debug " API Response: $1 "
2430 if [ " $type " = ' keygen' ]; then
2531 status=$( echo " $1 " | sed ' s/^.*\([' \' ' ]\)\([a-z]*\)' \' ' .*/\2/g' )
2632 if [ " $status " = " success" ]; then
@@ -30,6 +36,13 @@ parse_response() {
3036 message=" PAN-OS Key could not be set."
3137 fi
3238 else
39+ if [ " $type " = ' commit' ]; then
40+ job_id=$( echo " $1 " | sed ' s/^.*\(<job>\)\(.*\)<\/job>.*/\2/g' )
41+ _commit_job_id=$job_id
42+ elif [ " $type " = ' job_status' ]; then
43+ job_status=$( echo " $1 " | tr -d ' \n' | sed ' s/^.*<result>\([^<]*\)<\/result>.*/\1/g' )
44+ _commit_job_status=$job_status
45+ fi
3346 status=$( echo " $1 " | tr -d ' \n' | sed ' s/^.*"\([a-z]*\)".*/\1/g' )
3447 message=$( echo " $1 " | tr -d ' \n' | sed ' s/.*\(<result>\|<msg>\|<line>\)\([^<]*\).*/\2/g' )
3548 _debug " Firewall message: $message "
@@ -44,13 +57,13 @@ parse_response() {
4457# This function is used to deploy to the firewall
4558deployer () {
4659 content=" "
47- type=$1 # Types are keytest, keygen, cert, key, commit
60+ type=$1 # Types are keytest, keygen, cert, key, commit, job_status, push
4861 panos_url=" https://$_panos_host /api/"
62+ export _H1=" Content-Type: application/x-www-form-urlencoded"
4963
5064 # Test API Key by performing a lookup
5165 if [ " $type " = ' keytest' ]; then
5266 _debug " **** Testing saved API Key ****"
53- _H1=" Content-Type: application/x-www-form-urlencoded"
5467 # Get Version Info to test key
5568 content=" type=version&key=$_panos_key "
5669 # # Exclude all scopes for the empty commit
@@ -61,7 +74,6 @@ deployer() {
6174 # Generate API Key
6275 if [ " $type " = ' keygen' ]; then
6376 _debug " **** Generating new API Key ****"
64- _H1=" Content-Type: application/x-www-form-urlencoded"
6577 content=" type=keygen&user=$_panos_user &password=$_panos_pass "
6678 # content="$content${nl}--$delim${nl}Content-Disposition: form-data; type=\"keygen\"; user=\"$_panos_user\"; password=\"$_panos_pass\"${nl}Content-Type: application/octet-stream${nl}${nl}"
6779 fi
@@ -84,6 +96,9 @@ deployer() {
8496 if [ " $_panos_template " ]; then
8597 content=" $content ${nl} --$delim ${nl} Content-Disposition: form-data; name=\" target-tpl\" \r\n\r\n$_panos_template "
8698 fi
99+ if [ " $_panos_vsys " ]; then
100+ content=" $content ${nl} --$delim ${nl} Content-Disposition: form-data; name=\" target-tpl-vsys\" \r\n\r\n$_panos_vsys "
101+ fi
87102 fi
88103 if [ " $type " = ' key' ]; then
89104 panos_url=" ${panos_url} ?type=import"
@@ -96,6 +111,9 @@ deployer() {
96111 if [ " $_panos_template " ]; then
97112 content=" $content ${nl} --$delim ${nl} Content-Disposition: form-data; name=\" target-tpl\" \r\n\r\n$_panos_template "
98113 fi
114+ if [ " $_panos_vsys " ]; then
115+ content=" $content ${nl} --$delim ${nl} Content-Disposition: form-data; name=\" target-tpl-vsys\" \r\n\r\n$_panos_vsys "
116+ fi
99117 fi
100118 # Close multipart
101119 content=" $content ${nl} --$delim --${nl}${nl} "
@@ -106,7 +124,6 @@ deployer() {
106124 # Commit changes
107125 if [ " $type " = ' commit' ]; then
108126 _debug " **** Committing changes ****"
109- export _H1=" Content-Type: application/x-www-form-urlencoded"
110127 # Check for force commit - will commit ALL uncommited changes to the firewall. Use with caution!
111128 if [ " $FORCE " ]; then
112129 _debug " Force switch detected. Committing ALL changes to the firewall."
@@ -118,6 +135,20 @@ deployer() {
118135 content=" type=commit&action=partial&key=$_panos_key &cmd=$cmd "
119136 fi
120137
138+ # Query job status
139+ if [ " $type " = ' job_status' ]; then
140+ echo " **** Querying job $_commit_job_id status ****"
141+ cmd=$( printf " %s" " <show><jobs><id>$_commit_job_id </id></jobs></show>" | _url_encode)
142+ content=" type=op&key=$_panos_key &cmd=$cmd "
143+ fi
144+
145+ # Push changes
146+ if [ " $type " = ' push' ]; then
147+ echo " **** Pushing changes ****"
148+ cmd=$( printf " %s" " <commit-all><template-stack><name>$_panos_template_stack </name><admin><member>$_panos_user </member></admin></template-stack></commit-all>" | _url_encode)
149+ content=" type=commit&action=all&key=$_panos_key &cmd=$cmd "
150+ fi
151+
121152 response=$( _post " $content " " $panos_url " " " " POST" )
122153 parse_response " $response " " $type "
123154 # Saving response to variables
@@ -126,6 +157,8 @@ deployer() {
126157 if [ " $response_status " = " success" ]; then
127158 _debug " Successfully deployed $type "
128159 return 0
160+ elif [ " $_commit_job_status " ]; then
161+ _debug " Commit Job Status = $_commit_job_status "
129162 else
130163 _err " Deploy of type $type failed. Try deploying with --debug to troubleshoot."
131164 _debug " $message "
@@ -191,11 +224,31 @@ panos_deploy() {
191224 _getdeployconf PANOS_TEMPLATE
192225 fi
193226
227+ # PANOS_TEMPLATE_STACK
228+ if [ " $PANOS_TEMPLATE_STACK " ]; then
229+ _debug " Detected ENV variable PANOS_TEMPLATE_STACK. Saving to file."
230+ _savedeployconf PANOS_TEMPLATE_STACK " $PANOS_TEMPLATE_STACK " 1
231+ else
232+ _debug " Attempting to load variable PANOS_TEMPLATE_STACK from file."
233+ _getdeployconf PANOS_TEMPLATE_STACK
234+ fi
235+
236+ # PANOS_TEMPLATE_STACK
237+ if [ " $PANOS_VSYS " ]; then
238+ _debug " Detected ENV variable PANOS_VSYS. Saving to file."
239+ _savedeployconf PANOS_VSYS " $PANOS_VSYS " 1
240+ else
241+ _debug " Attempting to load variable PANOS_VSYS from file."
242+ _getdeployconf PANOS_VSYS
243+ fi
244+
194245 # Store variables
195246 _panos_host=$PANOS_HOST
196247 _panos_user=$PANOS_USER
197248 _panos_pass=$PANOS_PASS
198249 _panos_template=$PANOS_TEMPLATE
250+ _panos_template_stack=$PANOS_TEMPLATE_STACK
251+ _panos_vsys=$PANOS_VSYS
199252
200253 # Test API Key if found. If the key is invalid, the variable _panos_key will be unset.
201254 if [ " $_panos_host " ] && [ " $_panos_key " ]; then
@@ -229,6 +282,20 @@ panos_deploy() {
229282 deployer cert
230283 deployer key
231284 deployer commit
285+ if [ " $_panos_template_stack " ]; then
286+ # try to get job status for 20 times in 30 sec interval
287+ i=0
288+ while [ " $i " -lt $_COMMIT_WAIT_ITERATIONS ]; do
289+ deployer job_status
290+ if [ " $_commit_job_status " = " OK" ]; then
291+ echo " Commit finished!"
292+ break
293+ fi
294+ sleep $_COMMIT_WAIT_INTERVAL
295+ i=$(( i + 1 ))
296+ done
297+ deployer push
298+ fi
232299 fi
233300 fi
234301}
0 commit comments