Add support for vFWCL - multiple VNFs

Issue-ID: TEST-72
Change-Id: Ic6fe176ca5fdeac00cd5018aecf7824ec4eca287
Signed-off-by: Jerry Flood <jf9860@att.com>
diff --git a/robot/assets/keys/onap_dev.ppk b/robot/assets/keys/onap_dev.ppk
new file mode 100644
index 0000000..eb84cbe
--- /dev/null
+++ b/robot/assets/keys/onap_dev.ppk
@@ -0,0 +1,26 @@
+PuTTY-User-Key-File-2: ssh-rsa
+Encryption: none
+Comment: imported-openssh-key
+Public-Lines: 6
+AAAAB3NzaC1yc2EAAAADAQABAAABAQDKXDgoo3+WOqcUG8/5uUbk81+yczgwC4Y8
+ywTmuQqbNxlY1oQ0YxdMUqUnhitSXs5S/yRuAVOYHwGg2mCs20oAINrP+mxBI544
+AMIb9itPjCtgqtE2EWo6MmnFGbHB4Sx3XioE7F4VPsh7japsIwzOjbrQe+Mua1TG
+Q5d4nfEOQaaglXLLPFfuc7WbhbJbK6Q7rHqZfRcOwAMXgDoBqlyqKeiKwnumddo2
+RyNT8ljYmvB6buz7KnMinzo7qB0uktVT05FH9Rg0CTWH5norlG5qXgP2aukL0gk1
+ph8iAt7uYLf1ktp+LJI2gaF6L0/qli9EmVCSLr1uJ38Q8CBflhkh
+Private-Lines: 14
+AAABAQClDekkhI9ZqseCqFjPuKaxsizZMg+faJb6WSHLSxzyk1OSWY6F6FklgLeC
+8HW/fuLNYZyGOYDEsG20lMqL02Wdiy7OutS3oOS5iyzIf9a90HfFJi706el6RIpv
+INETcaXCS0T8tQrcS1RdKqTaBRC6HXJGAPbBcvw3pwQSdskatU6a/Kt2a3x6Dsqq
+inQcgEB/SbrDaJCUX9sbF2HVUwdq7aZK1Lk0ozr1FID9mrhjwWuQ6XC+vjG0Fqty
+XeMpR5iaQ73hex3FXQ8zOjkFbMwuHWSh1DSx70r5yFrrBqwQKnMsBqx4QDRf3fIE
+NUnWviaL+n+gwcXA07af4kaNUFUtAAAAgQD7jTUQBoWZ8mfc4Lp7PTzOep5njFIp
+FeXTzdg020G+/XKX1fu6Quj3kh/3UyhS8+tneqgDNhLDV0L3sH/H4qQVQUT7Eaij
+r/rnqXdNXRzcutiOQfs0Zm3vSm3vhDetKnc78jzPtoVegp7xr9XYq4pkvabuka8Q
+9kZs9XnLZyRPqwAAAIEAzfBRtIR6bJnoQqNyTZF92KnNjQw0GchnZxSoeHyaY9eN
+1MvOldv2+Y9sdvTVDCjww/6AydNtME7PI0Bod0isI70UdboLzmPei3ljNyv4RwFV
+y5r7sodTRKCfjgk0fwOKwntjrdQ//Vdvh3X9C8d/FjLdY6+9F1Vnuk+jwk1f3mMA
+AACBALHlChm+hPNF01VTc4srolW0ArCNGSbkX6jGdiCA0CVPbugJxgMGsorah25B
+rJg0/uB1M9NftSSp58ONkXUqx3VPy2jqJw/kSBqntsfNNEF86gEii3Ql68u0aIha
+ibZHRUMpMyXpgPsTl7xy4CovzFxbFPdDwg9FSSi4/L8KV+/G
+Private-MAC: 0b5005f6dad99d4ef75fe22b572e5497e5b34853
diff --git a/robot/assets/keys/onap_dev.pvt b/robot/assets/keys/onap_dev.pvt
new file mode 100644
index 0000000..81e334a
--- /dev/null
+++ b/robot/assets/keys/onap_dev.pvt
@@ -0,0 +1,27 @@
+-----BEGIN RSA PRIVATE KEY-----
+MIIEpQIBAAKCAQEAylw4KKN/ljqnFBvP+blG5PNfsnM4MAuGPMsE5rkKmzcZWNaE
+NGMXTFKlJ4YrUl7OUv8kbgFTmB8BoNpgrNtKACDaz/psQSOeOADCG/YrT4wrYKrR
+NhFqOjJpxRmxweEsd14qBOxeFT7Ie42qbCMMzo260HvjLmtUxkOXeJ3xDkGmoJVy
+yzxX7nO1m4WyWyukO6x6mX0XDsADF4A6AapcqinoisJ7pnXaNkcjU/JY2Jrwem7s
++ypzIp86O6gdLpLVU9ORR/UYNAk1h+Z6K5Rual4D9mrpC9IJNaYfIgLe7mC39ZLa
+fiySNoGhei9P6pYvRJlQki69bid/EPAgX5YZIQIDAQABAoIBAQClDekkhI9ZqseC
+qFjPuKaxsizZMg+faJb6WSHLSxzyk1OSWY6F6FklgLeC8HW/fuLNYZyGOYDEsG20
+lMqL02Wdiy7OutS3oOS5iyzIf9a90HfFJi706el6RIpvINETcaXCS0T8tQrcS1Rd
+KqTaBRC6HXJGAPbBcvw3pwQSdskatU6a/Kt2a3x6DsqqinQcgEB/SbrDaJCUX9sb
+F2HVUwdq7aZK1Lk0ozr1FID9mrhjwWuQ6XC+vjG0FqtyXeMpR5iaQ73hex3FXQ8z
+OjkFbMwuHWSh1DSx70r5yFrrBqwQKnMsBqx4QDRf3fIENUnWviaL+n+gwcXA07af
+4kaNUFUtAoGBAPuNNRAGhZnyZ9zguns9PM56nmeMUikV5dPN2DTbQb79cpfV+7pC
+6PeSH/dTKFLz62d6qAM2EsNXQvewf8fipBVBRPsRqKOv+uepd01dHNy62I5B+zRm
+be9Kbe+EN60qdzvyPM+2hV6CnvGv1dirimS9pu6RrxD2Rmz1ectnJE+rAoGBAM3w
+UbSEemyZ6EKjck2RfdipzY0MNBnIZ2cUqHh8mmPXjdTLzpXb9vmPbHb01Qwo8MP+
+gMnTbTBOzyNAaHdIrCO9FHW6C85j3ot5Yzcr+EcBVcua+7KHU0Sgn44JNH8DisJ7
+Y63UP/1Xb4d1/QvHfxYy3WOvvRdVZ7pPo8JNX95jAoGAIe5CIg8/JizUZa7KeKUh
+9pgDleQPkQsrHQ6/AyIwFBsLwf9THSS5V+uV9D57SfUs46Bf2U8J6N90YQSlt8iS
+aWuManFPVgT+yxDIzt6obf2mCEpOIBtQ6N4ZRh2HhQwdWTCrkzkDdGQaHG+jYL6C
+xGPwiG2ON7OAfGIAM7eN5lECgYEAhoRLWlaOgRGnHKAWsYQvZ67CjTdDcPPuVu6v
+fMQnNMA/7JeTwV+E205L0wfpgZ/cZKmBBlQMJlnUA3q2wfO+PTnse1mjDJU/cGtB
+22/lJLxChlQdxGeQhGtGzUhF+hEeOhrO6WSSx7CtMRZoy6Dr6lwfMFZCdVNcBd6v
+YOOZk3ECgYEAseUKGb6E80XTVVNziyuiVbQCsI0ZJuRfqMZ2IIDQJU9u6AnGAway
+itqHbkGsmDT+4HUz01+1JKnnw42RdSrHdU/LaOonD+RIGqe2x800QXzqASKLdCXr
+y7RoiFqJtkdFQykzJemA+xOXvHLgKi/MXFsU90PCD0VJKLj8vwpX78Y=
+-----END RSA PRIVATE KEY-----
diff --git a/robot/assets/keys/onap_dev_public.pub b/robot/assets/keys/onap_dev_public.pub
new file mode 100644
index 0000000..f5d879e
--- /dev/null
+++ b/robot/assets/keys/onap_dev_public.pub
@@ -0,0 +1,9 @@
+---- BEGIN SSH2 PUBLIC KEY ----
+Comment: "imported-openssh-key"
+AAAAB3NzaC1yc2EAAAADAQABAAABAQDKXDgoo3+WOqcUG8/5uUbk81+yczgwC4Y8
+ywTmuQqbNxlY1oQ0YxdMUqUnhitSXs5S/yRuAVOYHwGg2mCs20oAINrP+mxBI544
+AMIb9itPjCtgqtE2EWo6MmnFGbHB4Sx3XioE7F4VPsh7japsIwzOjbrQe+Mua1TG
+Q5d4nfEOQaaglXLLPFfuc7WbhbJbK6Q7rHqZfRcOwAMXgDoBqlyqKeiKwnumddo2
+RyNT8ljYmvB6buz7KnMinzo7qB0uktVT05FH9Rg0CTWH5norlG5qXgP2aukL0gk1
+ph8iAt7uYLf1ktp+LJI2gaF6L0/qli9EmVCSLr1uJ38Q8CBflhkh
+---- END SSH2 PUBLIC KEY ----
diff --git a/robot/assets/keys/onap_dev_public.txt b/robot/assets/keys/onap_dev_public.txt
new file mode 100644
index 0000000..838287f
--- /dev/null
+++ b/robot/assets/keys/onap_dev_public.txt
@@ -0,0 +1 @@
+ssh-rsa AAAAB3NzaC1yc2EAAAADAQABAAABAQDKXDgoo3+WOqcUG8/5uUbk81+yczgwC4Y8ywTmuQqbNxlY1oQ0YxdMUqUnhitSXs5S/yRuAVOYHwGg2mCs20oAINrP+mxBI544AMIb9itPjCtgqtE2EWo6MmnFGbHB4Sx3XioE7F4VPsh7japsIwzOjbrQe+Mua1TGQ5d4nfEOQaaglXLLPFfuc7WbhbJbK6Q7rHqZfRcOwAMXgDoBqlyqKeiKwnumddo2RyNT8ljYmvB6buz7KnMinzo7qB0uktVT05FH9Rg0CTWH5norlG5qXgP2aukL0gk1ph8iAt7uYLf1ktp+LJI2gaF6L0/qli9EmVCSLr1uJ38Q8CBflhkh imported-openssh-key
\ No newline at end of file
diff --git a/robot/assets/service_mappings.py b/robot/assets/service_mappings.py
index e0913ff..5a58bb9 100644
--- a/robot/assets/service_mappings.py
+++ b/robot/assets/service_mappings.py
@@ -4,21 +4,35 @@
 GLOBAL_SERVICE_FOLDER_MAPPING = {"vFW" : ['vFW'], \
                                  "vLB" : ['vLB'], \
                                  "vVG" : ['vVG'], \
-                                 "vCPE" : ['vCPE/infra', 'vCPE/vbng', 'vCPE/vbrgemu', 'vCPE/vgmux', 'vCPE/vgw'], 
+                                 "vCPE" : ['vCPE/infra', 'vCPE/vbng', 'vCPE/vbrgemu', 'vCPE/vgmux', 'vCPE/vgw'],
+                                 "vFWCL" : ['vFWCL/vFWSNK', 'vFWCL/vPKG'],
+                                 }
+
+'''
+Map the service to the list of VNFs to be orchestrated
+'''
+GLOBAL_SERVICE_VNF_MAPPING = {
+    "vFW"  : ['vFW'],
+    "vLB"  : ['vLB'],
+    "vVG"  : ['vVG'],
+    "vCPE" : ['vCPE'],
+    "vFWCL"  : ['vFWSNK', 'vPKG'],
                                  }
 
 '''
 This metadata identifes the preloads that need to be done for a VNF as there may be more than one (vLB)
-"template" maps to the parameters in the preload_paramenters.py  
+"template" maps to the parameters in the preload_paramenters.py
   - GLOBAL_PRELOAD_PARAMETERS[<testcase>][<template>] -
     i.e. GLOBAL_PRELOAD_PARAMETERS['Demo'][dnsscaling_preload.template']
 '''
 GLOBAL_SERVICE_TEMPLATE_MAPPING = {
-	"vFW"  : [{"isBase" : "true", "template" : "vfw_preload.template", "name_pattern": "base_vfw"}], 
+	"vFW"  : [{"isBase" : "true", "template" : "vfw_preload.template", "name_pattern": "base_vfw"}],
     "vLB"  : [{"isBase" : "true",   "template" : "vlb_preload.template", "name_pattern": "base_vlb"},
               {"isBase" : "false",  "template" : "dnsscaling_preload.template", "name_pattern": "dnsscaling", "prefix" : "vDNS_"}],
-    "vVG"  : [{"isBase" : "true",   "template" : "vvg_preload.template", "name_pattern": "base_vvg"}], 
-    "vCPE" : [{"isBase" : "true",  "template" : "vcpe_preload.template", "name_pattern": "base_clearwater"}], 
+    "vVG"  : [{"isBase" : "true",   "template" : "vvg_preload.template", "name_pattern": "base_vvg"}],
+    "vCPE" : [{"isBase" : "true",  "template" : "vcpe_preload.template", "name_pattern": "base_clearwater"}],
+    "vFWSNK" : [{"isBase" : "true",   "template" : "vfwsnk_preload.template", "name_pattern": "base_vfw"}],
+    "vPKG"   : [{"isBase" : "true",  "template" : "vpkg_preload.template", "name_pattern": "base_vpkg"}],
 }
 
 '''
@@ -28,4 +42,6 @@
                                  "vLB" : 'vlb_name_0',
                                  "vVG" : '',
                                  "vCPE" : '',
+                                 "vFWSNK" : 'vfw_name_0',
+                                 "vPKG" : 'vpg_name_0',
                                  }
diff --git a/robot/resources/asdc_interface.robot b/robot/resources/asdc_interface.robot
index 90bf952..76496cc 100644
--- a/robot/resources/asdc_interface.robot
+++ b/robot/resources/asdc_interface.robot
@@ -53,11 +53,13 @@
     [Arguments]    ${model_zip_path}   ${catalog_service_name}=
     ${catalog_service_id}=    Add ASDC Catalog Service    ${catalog_service_name}
     ${catalog_resource_ids}=    Create List
+    ${catalog_resources}=   Create Dictionary
     : FOR    ${zip}     IN     @{model_zip_path}
     \    ${loop_catalog_resource_id}=    Setup ASDC Catalog Resource    ${zip}
     \    Append To List    ${catalog_resource_ids}   ${loop_catalog_resource_id}
     \    ${loop_catalog_resource_resp}=    Get ASDC Catalog Resource    ${loop_catalog_resource_id}
     \    Add ASDC Resource Instance    ${catalog_service_id}    ${loop_catalog_resource_id}    ${loop_catalog_resource_resp['name']}
+    \    Set To Dictionary    ${catalog_resources}   ${loop_catalog_resource_id}=${loop_catalog_resource_resp}
     ${catalog_service_resp}=    Get ASDC Catalog Service    ${catalog_service_id}
     Checkin ASDC Catalog Service    ${catalog_service_id}
     Request Certify ASDC Catalog Service    ${catalog_service_id}
@@ -69,8 +71,8 @@
 	${catalog_service_resp}=    Get ASDC Catalog Service    ${catalog_service_id}
 	${vf_module}=    Find Element In Array    ${loop_catalog_resource_resp['groups']}    type    org.openecomp.groups.VfModule
 	Check Catalog Service Distributed    ${catalog_service_resp['uuid']}
-    [Return]    ${catalog_service_resp['name']}    ${loop_catalog_resource_resp['name']}    ${vf_module}   ${catalog_resource_ids}    ${catalog_service_id}
-    
+    [Return]    ${catalog_service_resp['name']}    ${loop_catalog_resource_resp['name']}    ${vf_module}   ${catalog_resource_ids}    ${catalog_service_id}   ${catalog_resources}
+
 Setup ASDC Catalog Resource
     [Documentation]    Creates all the steps a vf needs for an asdc catalog resource and returns the id
     [Arguments]    ${model_zip_path}
diff --git a/robot/resources/sdngc_interface.robot b/robot/resources/sdngc_interface.robot
index 2339ab5..5028644 100644
--- a/robot/resources/sdngc_interface.robot
+++ b/robot/resources/sdngc_interface.robot
@@ -83,7 +83,7 @@
 
 Preload Vnf
     [Arguments]    ${service_type_uuid}    ${generic_vnf_name}    ${generic_vnf_type}     ${vf_module_name}    ${vf_modules}    ${service}   ${uuid}
-    ${base_vf_module_type}=    Catenate    ''
+    ${base_vf_module_type}=    Catenate
     ${closedloop_vf_module}=    Create Dictionary
     ${templates}=    Get From Dictionary    ${GLOBAL_SERVICE_TEMPLATE_MAPPING}    ${service}
     :for    ${vf_module}    in      @{vf_modules}
diff --git a/robot/resources/test_templates/closedloop_test_template.robot b/robot/resources/test_templates/closedloop_test_template.robot
index 6930e56..1a13613 100644
--- a/robot/resources/test_templates/closedloop_test_template.robot
+++ b/robot/resources/test_templates/closedloop_test_template.robot
@@ -192,7 +192,7 @@
 	[Documentation]    VNF Orchestration for vFW
 	Log    VNF Orchestration flow TEST NAME=${TEST NAME}
 	Setup Orchestrate VNF    ${GLOBAL_AAI_CLOUD_OWNER}    SharedNode    OwnerType    v1    CloudZone
-	${stack_name}    ${service}=  Orchestrate VNF   ETE_CLP    vFW      vFW   ${TENANT_NAME}
+	${stack_name}    ${service}=  Orchestrate VNF   ETE_CLP    vFWCL      vFWCL   ${TENANT_NAME}
 	[Return]  ${stack_name}
 
  Orchestrate VNF vDNS closedloop
diff --git a/robot/resources/test_templates/model_test_template.robot b/robot/resources/test_templates/model_test_template.robot
index 4dce50a..98b3b1c 100644
--- a/robot/resources/test_templates/model_test_template.robot
+++ b/robot/resources/test_templates/model_test_template.robot
@@ -3,7 +3,7 @@
 Library           OperatingSystem
 Library            ArchiveLibrary
 Library           Collections
-Library           String 
+Library           String
 Resource          ../asdc_interface.robot
 
 Variables       ../../assets/service_mappings.py
@@ -25,16 +25,17 @@
     ${directory_list}=    Get From Dictionary    ${GLOBAL_SERVICE_FOLDER_MAPPING}    ${service}
     ${ziplist}=    Create List
     :for   ${directory}    in    @{directory_list}
-    \    ${zipname}=   Replace String    ${directory}    /    _     
+    \    ${zipname}=   Replace String    ${directory}    /    _
     \    ${zip}=    Catenate    ${ASDC_ZIP_DIRECTORY}/${zipname}.zip
     \    ${folder}=    Catenate    ${ASDC_ASSETS_DIRECTORY}/${directory}
     \    OperatingSystem.Create Directory    ${ASDC_ASSETS_DIRECTORY}/temp
     \    Create Zip From Files In Directory        ${folder}    ${zip}
     \    Append To List    ${ziplist}    ${zip}
-    ${catalog_service_name}    ${catalog_resource_name}    ${vf_modules}    ${catalog_resource_ids}   ${catalog_service_id}   Distribute Model From ASDC    ${ziplist}    ${catalog_service_name}
+    ${catalog_service_name}    ${catalog_resource_name}    ${vf_modules}    ${catalog_resource_ids}   ${catalog_service_id}   ${catalog_resources}   Distribute Model From ASDC    ${ziplist}    ${catalog_service_name}
     Set Test Variable   ${CATALOG_RESOURCE_IDS}   ${catalog_resource_ids}
     Set Test Variable   ${CATALOG_SERVICE_ID}   ${catalog_service_id}
-    [Return]    ${catalog_service_name}    ${catalog_resource_name}    ${vf_modules}
+    Set Test Variable   ${CATALOG_RESOURCES}   ${catalog_resources}
+    [Return]    ${catalog_service_name}    ${catalog_resource_name}    ${vf_modules}   ${catalog_resources}
 
 
 
diff --git a/robot/resources/test_templates/vnf_orchestration_test_template.robot b/robot/resources/test_templates/vnf_orchestration_test_template.robot
index 1e3bd76..807647d 100644
--- a/robot/resources/test_templates/vnf_orchestration_test_template.robot
+++ b/robot/resources/test_templates/vnf_orchestration_test_template.robot
@@ -33,6 +33,7 @@
 ${REGIONS}
 ${CUSTOMER_NAME}
 ${STACK_NAME}
+${STACK_NAMES}
 ${SERVICE}
 ${VVG_SERVER_ID}
 ${SERVICE_INSTANCE_ID}
@@ -51,11 +52,11 @@
     ${uuid}=    Generate UUID
     Set Test Variable    ${CUSTOMER_NAME}    ${customer_name}_${uuid}
     Set Test Variable    ${SERVICE}    ${service}
-    ${vnf_name}=    Catenate    Vnf_Ete_Name${uuid}
+    ${list}=    Create List
+    Set Test Variable    ${STACK_NAMES}   ${list}
     ${service_name}=    Catenate    Service_Ete_Name${uuid}
     ${service_type}=    Set Variable    ${service}
-    ${vf_module_name}=    Catenate    Vfmodule_Ete_Name${uuid}
-    ${service_model_type}     ${vnf_type}    ${vf_modules} =    Model Distribution For Directory    ${service}
+    ${service_model_type}     ${vnf_type}    ${vf_modules}   ${catalog_resources}=    Model Distribution For Directory    ${service}
     Run Keyword If   '${service}' == 'vVG'    Create VVG Server    ${uuid}
     Create Customer For VNF    ${CUSTOMER_NAME}    ${CUSTOMER_NAME}    INFRA    ${service_type}    ${GLOBAL_AAI_CLOUD_OWNER}
     Setup Browser
@@ -63,17 +64,62 @@
     ${service_instance_id}=   Wait Until Keyword Succeeds    300s   5s    Create VID Service Instance    ${customer_name}    ${service_model_type}    ${service}     ${service_name}
     Set Test Variable   ${SERVICE_INSTANCE_ID}   ${service_instance_id}
     Validate Service Instance    ${service_instance_id}    ${service}      ${customer_name}
-    Wait Until Keyword Succeeds    300s   5s    Create VID VNF    ${service_instance_id}    ${vnf_name}    ${product_family}    ${lcp_region}    ${tenant}    ${vnf_type}   ${CUSTOMER_NAME}
-    ${vf_module_type}   ${closedloop_vf_module}=   Preload Vnf    ${service_instance_id}   ${vnf_name}   ${vnf_type}   ${vf_module_name}    ${vf_modules}    ${service}    ${uuid}
-    ${vf_module_id}=   Create VID VNF module    ${service_instance_id}    ${vf_module_name}    ${lcp_region}    ${tenant}     ${vf_module_type}   ${CUSTOMER_NAME}
-    ${generic_vnf}=   Validate Generic VNF    ${vnf_name}    ${vnf_type}    ${service_instance_id}
-    VLB Closed Loop Hack   ${service}   ${generic_vnf}   ${closedloop_vf_module}
-    Set Test Variable    ${STACK_NAME}   ${vf_module_name}
-    Execute Heatbridge    ${vf_module_name}    ${service_instance_id}    ${service}
-    Validate VF Module      ${vf_module_name}    ${service}
+    ${vnflist}=   Get From Dictionary    ${GLOBAL_SERVICE_VNF_MAPPING}    ${service}
+    :for   ${vnf}   in   @{vnflist}
+    \   ${vnf_name}=    Catenate    Ete_${vnf}_${uuid}
+    \   ${vf_module_name}=    Catenate    Vfmodule_Ete_${vnf}_${uuid}
+    \   ${vnf_type}=   Get VNF Type   ${catalog_resources}   ${vnf}
+    \   ${vf_module}=    Get VF Module    ${catalog_resources}   ${vnf}
+    \   Append To List   ${STACK_NAMES}   ${vf_module_name}
+    \   Wait Until Keyword Succeeds    300s   5s    Create VID VNF    ${service_instance_id}    ${vnf_name}    ${product_family}    ${lcp_region}    ${tenant}    ${vnf_type}   ${CUSTOMER_NAME}
+    \   ${vf_module_type}   ${closedloop_vf_module}=   Preload Vnf    ${service_instance_id}   ${vnf_name}   ${vnf_type}   ${vf_module_name}    ${vf_module}    ${vnf}    ${uuid}
+    \   ${vf_module_id}=   Create VID VNF module    ${service_instance_id}    ${vf_module_name}    ${lcp_region}    ${tenant}     ${vf_module_type}   ${CUSTOMER_NAME}   ${vnf_name}
+    \   ${generic_vnf}=   Validate Generic VNF    ${vnf_name}    ${vnf_type}    ${service_instance_id}
+    \   VLB Closed Loop Hack   ${service}   ${generic_vnf}   ${closedloop_vf_module}
+    \   Set Test Variable    ${STACK_NAME}   ${vf_module_name}
+    \   Append To List   ${STACK_NAMES}   ${STACK_NAME}
+    \   Execute Heatbridge    ${vf_module_name}    ${service_instance_id}    ${vnf}
+    \   Validate VF Module      ${vf_module_name}    ${vnf}
     [Return]     ${vf_module_name}    ${service}
 
 
+Get VNF Type
+    [Documentation]    To support services with multiple VNFs, we need to dig the vnf type out of the SDC catalog resources to select in the VID UI
+    [Arguments]   ${resources}   ${vnf}
+    ${cr}=   Get Catalog Resource    ${resources}    ${vnf}
+    ${vnf_type}=   Get From Dictionary   ${cr}   name
+    [Return]   ${vnf_type}
+
+Get VF Module
+    [Documentation]    To support services with multiple VNFs, we need to dig the vnf type out of the SDC catalog resources to select in the VID UI
+    [Arguments]   ${resources}   ${vnf}
+    ${cr}=   Get Catalog Resource    ${resources}    ${vnf}
+    ${vf_module}=    Find Element In Array    ${cr['groups']}    type    org.openecomp.groups.VfModule
+    [Return]  ${vf_module}
+
+Get Catalog Resource
+    [Documentation]    To support services with multiple VNFs, we need to dig the vnf type out of the SDC catalog resources to select in the VID UI
+    [Arguments]   ${resources}   ${vnf}
+
+    ${base_name}=  Get Name Pattern   ${vnf}
+    ${keys}=    Get Dictionary Keys    ${resources}
+
+    :for   ${key}   in    @{keys}
+    \    ${cr}=   Get From Dictionary    ${resources}    ${key}
+    \    Return From Keyword If   '${base_name}' in '${cr['allArtifacts']['heat1']['artifactDisplayName']}'    ${cr}
+    Fail    Unable to find catalog resource for ${vnf} ${base_name}
+
+Get Name Pattern
+    [Documentation]    To support services with multiple VNFs, we need to dig the vnf type out of the SDC catalog resources to select in the VID UI
+    [Arguments]   ${vnf}
+    ${list}=   Get From Dictionary    ${GLOBAL_SERVICE_TEMPLATE_MAPPING}   ${vnf}
+    :for    ${dict}   in   @{list}
+    \   ${base_name}=   Get From Dictionary    ${dict}    name_pattern
+    \   Return From Keyword If   '${dict['isBase']}' == 'true'   ${base_name}
+    Fail  Unable to locate base name pattern
+
+
+
 Create Customer For VNF
     [Documentation]    VNF Orchestration Test setup....
     ...                Create Tenant if not exists, Create Customer, Create Service and related relationships
diff --git a/robot/resources/vid/create_vid_vnf.robot b/robot/resources/vid/create_vid_vnf.robot
index 67e308c..4173762 100644
--- a/robot/resources/vid/create_vid_vnf.robot
+++ b/robot/resources/vid/create_vid_vnf.robot
@@ -81,7 +81,7 @@
     Poll MSO Get Request    ${GLOBAL_MSO_STATUS_PATH}${request_id}   COMPLETE
 
 Create VID VNF module
-    [Arguments]    ${service_instance_id}    ${vf_module_name}    ${lcp_region}    ${TENANT}    ${VNF_TYPE}   ${customer}
+    [Arguments]    ${service_instance_id}    ${vf_module_name}    ${lcp_region}    ${TENANT}    ${VNF_TYPE}   ${customer}   ${vnf_name}
     Go To VID HOME
     Click Link       xpath=//div[@heading = 'Search for Existing Service Instances']/a
     Wait Until Page Contains    Please search by    timeout=${GLOBAL_VID_UI_TIMEOUT_MEDIUM}
@@ -98,7 +98,7 @@
     #Wait Until Page Contains Element    xpath=//div[@class='statusLine']    timeout=120s
     #Wait Until Element Is Not Visible    xpath=//div[@class='statusLine aaiHidden']    timeout=120s
     #Wait Until Element Is Visible    button=Add VF-Module   timeout=120s
-    Click Element    button=Add VF-Module
+    Click Element     xpath=//div[contains(.,'${vnf_name}')]/div/button[contains(.,'Add VF-Module')]
 
     # This is where firefox breaks. Th elink never becomes visible when run with the script.
     Click Element    link=${vnf_type}
diff --git a/robot/testsuites/vnf-orchestration.robot b/robot/testsuites/vnf-orchestration.robot
index d7ae16f..450b63f 100644
--- a/robot/testsuites/vnf-orchestration.robot
+++ b/robot/testsuites/vnf-orchestration.robot
@@ -15,6 +15,7 @@
     [Tags]    ete    instantiate
 Instantiate Virtual Volume Group    ETE_Customer    vVG      vVG             ${TENANT_NAME}
     [Tags]    ete    instantiate
+Instantiate Virtual FirewallCL      ETE_Customer    vFWCL      vFWCL         ${TENANT_NAME}