Remove Mistral
This patch is a part of Legacy APIs deprecation. A Mistral workflow is created when NS is created, however, Tacker doesn't have actual action scripts. Therefore, even though a Mistral workflow is created, it never runs successfully due to the absence of specified scripts. This patch removes the dependency on Mistral for the legacy NS create/delete APIs and also remove Mistral from Tacker entirely, as there's no longer any place to use Mistral. Implements: blueprint deprecate-legacy-apis Change-Id: Iee5d109e4fdb9546730164aea94985b1c535bbc6
This commit is contained in:
parent
ed0ba564be
commit
dd14850ba6
@ -121,12 +121,9 @@
|
|||||||
- openstack/horizon
|
- openstack/horizon
|
||||||
- openstack/barbican
|
- openstack/barbican
|
||||||
- openstack/heat
|
- openstack/heat
|
||||||
- openstack/mistral
|
|
||||||
- openstack/mistral-dashboard
|
|
||||||
- openstack/networking-sfc
|
- openstack/networking-sfc
|
||||||
- openstack/python-barbicanclient
|
- openstack/python-barbicanclient
|
||||||
- openstack/python-blazarclient
|
- openstack/python-blazarclient
|
||||||
- openstack/python-mistralclient
|
|
||||||
- openstack/python-tackerclient
|
- openstack/python-tackerclient
|
||||||
- openstack/tacker
|
- openstack/tacker
|
||||||
- openstack/tacker-horizon
|
- openstack/tacker-horizon
|
||||||
@ -168,7 +165,6 @@
|
|||||||
networking-sfc: https://opendev.org/openstack/networking-sfc
|
networking-sfc: https://opendev.org/openstack/networking-sfc
|
||||||
aodh: https://opendev.org/openstack/aodh
|
aodh: https://opendev.org/openstack/aodh
|
||||||
barbican: https://opendev.org/openstack/barbican
|
barbican: https://opendev.org/openstack/barbican
|
||||||
mistral: https://opendev.org/openstack/mistral
|
|
||||||
blazar: https://opendev.org/openstack/blazar
|
blazar: https://opendev.org/openstack/blazar
|
||||||
fenix: https://opendev.org/x/fenix
|
fenix: https://opendev.org/x/fenix
|
||||||
devstack_services:
|
devstack_services:
|
||||||
@ -387,14 +383,12 @@
|
|||||||
- openstack/horizon
|
- openstack/horizon
|
||||||
- openstack/keystone
|
- openstack/keystone
|
||||||
- openstack/kuryr-kubernetes
|
- openstack/kuryr-kubernetes
|
||||||
- openstack/mistral
|
|
||||||
- openstack/neutron
|
- openstack/neutron
|
||||||
- openstack/nova
|
- openstack/nova
|
||||||
- openstack/octavia
|
- openstack/octavia
|
||||||
- openstack/placement
|
- openstack/placement
|
||||||
- openstack/python-barbicanclient
|
- openstack/python-barbicanclient
|
||||||
- openstack/python-blazarclient
|
- openstack/python-blazarclient
|
||||||
- openstack/python-mistralclient
|
|
||||||
- openstack/python-octaviaclient
|
- openstack/python-octaviaclient
|
||||||
- openstack/python-tackerclient
|
- openstack/python-tackerclient
|
||||||
- openstack/tacker
|
- openstack/tacker
|
||||||
@ -404,7 +398,6 @@
|
|||||||
devstack_plugins:
|
devstack_plugins:
|
||||||
barbican: https://opendev.org/openstack/barbican
|
barbican: https://opendev.org/openstack/barbican
|
||||||
heat: https://opendev.org/openstack/heat
|
heat: https://opendev.org/openstack/heat
|
||||||
mistral: https://opendev.org/openstack/mistral
|
|
||||||
neutron: https://opendev.org/openstack/neutron
|
neutron: https://opendev.org/openstack/neutron
|
||||||
octavia: https://opendev.org/openstack/octavia
|
octavia: https://opendev.org/openstack/octavia
|
||||||
devstack_services:
|
devstack_services:
|
||||||
|
@ -34,11 +34,10 @@ Q_AGENT=ovn
|
|||||||
# Disable security groups
|
# Disable security groups
|
||||||
LIBVIRT_FIREWALL_DRIVER=nova.virt.firewall.NoopFirewallDriver
|
LIBVIRT_FIREWALL_DRIVER=nova.virt.firewall.NoopFirewallDriver
|
||||||
|
|
||||||
# Enable heat, networking-sfc, barbican and mistral
|
# Enable heat, networking-sfc and barbican
|
||||||
enable_plugin heat https://opendev.org/openstack/heat master
|
enable_plugin heat https://opendev.org/openstack/heat master
|
||||||
enable_plugin networking-sfc https://opendev.org/openstack/networking-sfc master
|
enable_plugin networking-sfc https://opendev.org/openstack/networking-sfc master
|
||||||
enable_plugin barbican https://opendev.org/openstack/barbican master
|
enable_plugin barbican https://opendev.org/openstack/barbican master
|
||||||
enable_plugin mistral https://opendev.org/openstack/mistral master
|
|
||||||
|
|
||||||
# Ceilometer
|
# Ceilometer
|
||||||
#CEILOMETER_PIPELINE_INTERVAL=300
|
#CEILOMETER_PIPELINE_INTERVAL=300
|
||||||
|
@ -34,12 +34,11 @@ Q_AGENT=ovn
|
|||||||
# Disable security groups
|
# Disable security groups
|
||||||
LIBVIRT_FIREWALL_DRIVER=nova.virt.firewall.NoopFirewallDriver
|
LIBVIRT_FIREWALL_DRIVER=nova.virt.firewall.NoopFirewallDriver
|
||||||
|
|
||||||
# Enable neutron, heat, networking-sfc, barbican and mistral
|
# Enable neutron, heat, networking-sfc and barbican
|
||||||
enable_plugin neutron https://opendev.org/openstack/neutron master
|
enable_plugin neutron https://opendev.org/openstack/neutron master
|
||||||
enable_plugin heat https://opendev.org/openstack/heat master
|
enable_plugin heat https://opendev.org/openstack/heat master
|
||||||
enable_plugin networking-sfc https://opendev.org/openstack/networking-sfc master
|
enable_plugin networking-sfc https://opendev.org/openstack/networking-sfc master
|
||||||
enable_plugin barbican https://opendev.org/openstack/barbican master
|
enable_plugin barbican https://opendev.org/openstack/barbican master
|
||||||
enable_plugin mistral https://opendev.org/openstack/mistral master
|
|
||||||
|
|
||||||
# Ceilometer
|
# Ceilometer
|
||||||
#CEILOMETER_PIPELINE_INTERVAL=300
|
#CEILOMETER_PIPELINE_INTERVAL=300
|
||||||
|
@ -24,5 +24,4 @@ TACKER_MODE=standalone
|
|||||||
USE_BARBICAN=True
|
USE_BARBICAN=True
|
||||||
enable_plugin networking-sfc ${GIT_BASE}/openstack/networking-sfc
|
enable_plugin networking-sfc ${GIT_BASE}/openstack/networking-sfc
|
||||||
enable_plugin barbican ${GIT_BASE}/openstack/barbican
|
enable_plugin barbican ${GIT_BASE}/openstack/barbican
|
||||||
enable_plugin mistral ${GIT_BASE}/openstack/mistral
|
|
||||||
enable_plugin tacker ${GIT_BASE}/openstack/tacker
|
enable_plugin tacker ${GIT_BASE}/openstack/tacker
|
||||||
|
@ -16,7 +16,6 @@ redirectmatch 301 ^/tacker/([^/]+)/devref/vnfd_template_parameterization.html$ ^
|
|||||||
redirectmatch 301 ^/tacker/([^/]+)/devref/vnffgd_template_description.html$ ^/tacker/$1/contributor/vnffgd_template_description.html
|
redirectmatch 301 ^/tacker/([^/]+)/devref/vnffgd_template_description.html$ ^/tacker/$1/contributor/vnffgd_template_description.html
|
||||||
redirectmatch 301 ^/tacker/([^/]+)/devref/vnfm_usage_guide.html$ ^/tacker/$1/user/vnfm_usage_guide.html
|
redirectmatch 301 ^/tacker/([^/]+)/devref/vnfm_usage_guide.html$ ^/tacker/$1/user/vnfm_usage_guide.html
|
||||||
redirectmatch 301 ^/tacker/([^/]+)/policies/dev-process.html$ ^/tacker/$1/contributor/dev-process.html
|
redirectmatch 301 ^/tacker/([^/]+)/policies/dev-process.html$ ^/tacker/$1/contributor/dev-process.html
|
||||||
redirectmatch 301 ^/tacker/([^/]+)/devref/mistral_workflows_usage_guide.html$ ^/tacker/$1/reference/mistral_workflows_usage_guide.html
|
|
||||||
redirectmatch 301 ^/tacker/([^/]+)/devref/alarm_monitoring_usage_guide.html$ ^/tacker/$1/user/alarm_monitoring_usage_guide.html
|
redirectmatch 301 ^/tacker/([^/]+)/devref/alarm_monitoring_usage_guide.html$ ^/tacker/$1/user/alarm_monitoring_usage_guide.html
|
||||||
redirectmatch 301 ^/tacker/([^/]+)/devref/enhanced_placement_awareness_usage_guide.html$ ^/tacker/$1/user/enhanced_placement_awareness_usage_guide.html
|
redirectmatch 301 ^/tacker/([^/]+)/devref/enhanced_placement_awareness_usage_guide.html$ ^/tacker/$1/user/enhanced_placement_awareness_usage_guide.html
|
||||||
redirectmatch 301 ^/tacker/([^/]+)/devref/multisite_vim_usage_guide.html$ ^/tacker/$1/user/multisite_vim_usage_guide.html
|
redirectmatch 301 ^/tacker/([^/]+)/devref/multisite_vim_usage_guide.html$ ^/tacker/$1/user/multisite_vim_usage_guide.html
|
||||||
|
@ -1,124 +0,0 @@
|
|||||||
..
|
|
||||||
Copyright 2014-2015 OpenStack Foundation
|
|
||||||
All Rights Reserved.
|
|
||||||
|
|
||||||
Licensed under the Apache License, Version 2.0 (the "License"); you may
|
|
||||||
not use this file except in compliance with the License. You may obtain
|
|
||||||
a copy of the License at
|
|
||||||
|
|
||||||
http://www.apache.org/licenses/LICENSE-2.0
|
|
||||||
|
|
||||||
Unless required by applicable law or agreed to in writing, software
|
|
||||||
distributed under the License is distributed on an "AS IS" BASIS, WITHOUT
|
|
||||||
WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the
|
|
||||||
License for the specific language governing permissions and limitations
|
|
||||||
under the License.
|
|
||||||
|
|
||||||
===============================
|
|
||||||
Mistral workflow VIM monitoring
|
|
||||||
===============================
|
|
||||||
|
|
||||||
For the purpose to make tacker server scale, the mistral workflow is used to
|
|
||||||
re-implement the VIM monitoring feature.
|
|
||||||
|
|
||||||
The main monitoring process is like this:
|
|
||||||
|
|
||||||
- user registers a VIM
|
|
||||||
- tacker server saves it into database
|
|
||||||
- tacker server generates a mistral workflow and executes it
|
|
||||||
- the VIM monitor mistral action is executed and do the monitoring, if there
|
|
||||||
is status change, it will RPC call conductor
|
|
||||||
- the conductor changes the VIM status
|
|
||||||
|
|
||||||
|
|
||||||
Feature exploration
|
|
||||||
===================
|
|
||||||
|
|
||||||
Firstly register a VIM:
|
|
||||||
|
|
||||||
.. code-block:: console
|
|
||||||
|
|
||||||
$ openstack vim register --config-file ~/testvim_config.yaml testvim2 -c id -c name -c status
|
|
||||||
Created a new vim:
|
|
||||||
+--------+--------------------------------------+
|
|
||||||
| Field | Value |
|
|
||||||
+--------+--------------------------------------+
|
|
||||||
| id | 4406cf8f-f2af-46cc-bfb9-e00add5805b7 |
|
|
||||||
| name | testvim2 |
|
|
||||||
| status | PENDING |
|
|
||||||
+--------+--------------------------------------+
|
|
||||||
|
|
||||||
..
|
|
||||||
|
|
||||||
The registered VIM's id is '4406cf8f-f2af-46cc-bfb9-e00add5805b7', after this,
|
|
||||||
there is a mistral workflow named as
|
|
||||||
'vim_id_4406cf8f-f2af-46cc-bfb9-e00add5805b7', is generated in mistral:
|
|
||||||
|
|
||||||
.. code-block:: console
|
|
||||||
|
|
||||||
$ openstack workflow list --filter name=vim_id_4406cf8f-f2af-46cc-bfb9-e00add5805b7 -c ID -c Name
|
|
||||||
+--------------------------------------+---------------------------------------------+
|
|
||||||
| ID | Name |
|
|
||||||
+--------------------------------------+---------------------------------------------+
|
|
||||||
| 0cd0deff-6132-4ee2-a181-1c877cd594cc | vim_id_4406cf8f-f2af-46cc-bfb9-e00add5805b7 |
|
|
||||||
+--------------------------------------+---------------------------------------------+
|
|
||||||
|
|
||||||
..
|
|
||||||
|
|
||||||
and it is executed:
|
|
||||||
|
|
||||||
.. code-block:: console
|
|
||||||
|
|
||||||
$ openstack workflow execution list --filter workflow_name=vim_id_4406cf8f-f2af-46cc-bfb9-e00add5805b7 -c ID -c 'Workflow name' -c State
|
|
||||||
+--------------------------------------+---------------------------------------------+---------+
|
|
||||||
| ID | Workflow name | State |
|
|
||||||
+--------------------------------------+---------------------------------------------+---------+
|
|
||||||
| 99ced0e2-be09-4219-ab94-299df8ee8789 | vim_id_4406cf8f-f2af-46cc-bfb9-e00add5805b7 | RUNNING |
|
|
||||||
+--------------------------------------+---------------------------------------------+---------+
|
|
||||||
|
|
||||||
..
|
|
||||||
|
|
||||||
The monitoring task is running too:
|
|
||||||
|
|
||||||
.. code-block:: console
|
|
||||||
|
|
||||||
$ openstack task execution list --filter workflow_name=vim_id_4406cf8f-f2af-46cc-bfb9-e00add5805b7 -c ID -c 'Workflow name' -c Name -c State
|
|
||||||
+--------------------------------------+-----------------------------+---------------------------------------------+---------+
|
|
||||||
| ID | Name | Workflow name | State |
|
|
||||||
+--------------------------------------+-----------------------------+---------------------------------------------+---------+
|
|
||||||
| f2fe2904-6ff2-4531-9bd0-4c998ef1515f | monitor_ping_vimPingVIMTASK | vim_id_4406cf8f-f2af-46cc-bfb9-e00add5805b7 | RUNNING |
|
|
||||||
+--------------------------------------+-----------------------------+---------------------------------------------+---------+
|
|
||||||
|
|
||||||
..
|
|
||||||
|
|
||||||
Of course, the VIM's state is in 'REACHABLE' status:
|
|
||||||
|
|
||||||
.. code-block:: console
|
|
||||||
|
|
||||||
$ openstack vim list --name testvim2 -c id -c name -c status
|
|
||||||
+--------------------------------------+----------+-----------+
|
|
||||||
| id | name | status |
|
|
||||||
+--------------------------------------+----------+-----------+
|
|
||||||
| 4406cf8f-f2af-46cc-bfb9-e00add5805b7 | testvim2 | REACHABLE |
|
|
||||||
+--------------------------------------+----------+-----------+
|
|
||||||
|
|
||||||
..
|
|
||||||
|
|
||||||
The deletion of VIM will lead to removal of all of these mistral resources.
|
|
||||||
|
|
||||||
|
|
||||||
Rabbitmq queues
|
|
||||||
===============
|
|
||||||
|
|
||||||
Each mistral VIM monitoring action is listening on three queues:
|
|
||||||
|
|
||||||
.. code-block:: console
|
|
||||||
|
|
||||||
~/tacker$ sudo rabbitmqctl list_queues | grep -i KILL_ACTION
|
|
||||||
KILL_ACTION 0
|
|
||||||
KILL_ACTION.4406cf8f-f2af-46cc-bfb9-e00add5805b7 0
|
|
||||||
KILL_ACTION_fanout_a8118e2e18b9443986a1b37f7b082ab9 0
|
|
||||||
|
|
||||||
..
|
|
||||||
|
|
||||||
But only KILL_ACTION with VIM id as suffix is used.
|
|
@ -114,7 +114,6 @@ Install Tacker
|
|||||||
enable_neutron: "no"
|
enable_neutron: "no"
|
||||||
enable_nova: "no"
|
enable_nova: "no"
|
||||||
enable_barbican: "yes"
|
enable_barbican: "yes"
|
||||||
enable_mistral: "yes"
|
|
||||||
enable_tacker: "yes"
|
enable_tacker: "yes"
|
||||||
enable_heat: "no"
|
enable_heat: "no"
|
||||||
enable_openvswitch: "no"
|
enable_openvswitch: "no"
|
||||||
@ -181,10 +180,6 @@ Install Tacker
|
|||||||
11b5ccf91d86 kolla/centos-source-barbican-worker:ussuri barbican_worker
|
11b5ccf91d86 kolla/centos-source-barbican-worker:ussuri barbican_worker
|
||||||
4a5224d14f36 kolla/centos-source-barbican-keystone-listener:ussuri barbican_keystone_listener
|
4a5224d14f36 kolla/centos-source-barbican-keystone-listener:ussuri barbican_keystone_listener
|
||||||
a169e7aed0b6 kolla/centos-source-barbican-api:ussuri barbican_api
|
a169e7aed0b6 kolla/centos-source-barbican-api:ussuri barbican_api
|
||||||
2b3b0341b562 kolla/centos-source-mistral-executor:ussuri mistral_executor
|
|
||||||
6c69bbdf6aea kolla/centos-source-mistral-event-engine:ussuri mistral_event_engine
|
|
||||||
d035295fe9f0 kolla/centos-source-mistral-engine:ussuri mistral_engine
|
|
||||||
72f52de2fb77 kolla/centos-source-mistral-api:ussuri mistral_api
|
|
||||||
07ecaad80542 kolla/centos-source-horizon:ussuri horizon
|
07ecaad80542 kolla/centos-source-horizon:ussuri horizon
|
||||||
7e6ac94ea505 kolla/centos-source-keystone:ussuri keystone
|
7e6ac94ea505 kolla/centos-source-keystone:ussuri keystone
|
||||||
2b16b169ed18 kolla/centos-source-keystone-fernet:ussuri keystone_fernet
|
2b16b169ed18 kolla/centos-source-keystone-fernet:ussuri keystone_fernet
|
||||||
|
@ -33,12 +33,11 @@ Pre-requisites
|
|||||||
|
|
||||||
#. Install required components.
|
#. Install required components.
|
||||||
|
|
||||||
Ensure that all required OpenStack components i.e. Keystone, Mistral,
|
Ensure that all required OpenStack components i.e. Keystone, Barbican and
|
||||||
Barbican and Horizon are installed. Refer the list below for installation
|
Horizon are installed. Refer the list below for installation of these
|
||||||
of these OpenStack components on different Operating Systems.
|
OpenStack components on different Operating Systems.
|
||||||
|
|
||||||
* https://docs.openstack.org/keystone/latest/install/index.html
|
* https://docs.openstack.org/keystone/latest/install/index.html
|
||||||
* https://docs.openstack.org/mistral/latest/admin/install/index.html
|
|
||||||
* https://docs.openstack.org/barbican/latest/install/install.html
|
* https://docs.openstack.org/barbican/latest/install/install.html
|
||||||
* https://docs.openstack.org/horizon/latest/install/index.html
|
* https://docs.openstack.org/horizon/latest/install/index.html
|
||||||
|
|
||||||
|
@ -22,7 +22,6 @@ Reference
|
|||||||
:maxdepth: 1
|
:maxdepth: 1
|
||||||
|
|
||||||
vim_config.rst
|
vim_config.rst
|
||||||
mistral_workflows_usage_guide.rst
|
|
||||||
block_storage_usage_guide.rst
|
block_storage_usage_guide.rst
|
||||||
reservation_policy_usage_guide.rst
|
reservation_policy_usage_guide.rst
|
||||||
maintenance_usage_guide.rst
|
maintenance_usage_guide.rst
|
||||||
|
@ -1,509 +0,0 @@
|
|||||||
..
|
|
||||||
Licensed under the Apache License, Version 2.0 (the "License"); you may
|
|
||||||
not use this file except in compliance with the License. You may obtain
|
|
||||||
a copy of the License at
|
|
||||||
|
|
||||||
http://www.apache.org/licenses/LICENSE-2.0
|
|
||||||
|
|
||||||
Unless required by applicable law or agreed to in writing, software
|
|
||||||
distributed under the License is distributed on an "AS IS" BASIS, WITHOUT
|
|
||||||
WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the
|
|
||||||
License for the specific language governing permissions and limitations
|
|
||||||
under the License.
|
|
||||||
|
|
||||||
.. _ref-mistral:
|
|
||||||
|
|
||||||
============================
|
|
||||||
Mistral workflows for Tacker
|
|
||||||
============================
|
|
||||||
|
|
||||||
.. warning::
|
|
||||||
Legacy Tacker features excluding VIM feature are deprecated
|
|
||||||
and will be removed in the first major release after the Tacker server
|
|
||||||
version 9.0.0 (2023.1 Antelope release).
|
|
||||||
|
|
||||||
OpenStack Mistral already integrated with Tacker. The Tenant User or Operator
|
|
||||||
can make use of tacker actions to create custom Mistral Workflows. This
|
|
||||||
document describes the usage of OpenStackClient CLI to validate, create
|
|
||||||
and executing Tacker workflows.
|
|
||||||
|
|
||||||
|
|
||||||
References
|
|
||||||
~~~~~~~~~~
|
|
||||||
|
|
||||||
- `Mistral workflow samples <https://github.com/openstack/tacker/tree/master/samples/mistral/workflows>`_.
|
|
||||||
- `Mistral Client / CLI Guide <https://docs.openstack.org/mistral/latest/admin/install/mistralclient_guide.html>`_.
|
|
||||||
|
|
||||||
Workflow definition file validation
|
|
||||||
~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
|
|
||||||
Validate workflow definition files before registering with Mistral.
|
|
||||||
|
|
||||||
::
|
|
||||||
|
|
||||||
usage: openstack workflow validate <definition>
|
|
||||||
|
|
||||||
::
|
|
||||||
|
|
||||||
$ openstack workflow validate create_vnf.yaml
|
|
||||||
|
|
||||||
+-------+-------+
|
|
||||||
| Field | Value |
|
|
||||||
+-------+-------+
|
|
||||||
| Valid | True |
|
|
||||||
| Error | None |
|
|
||||||
+-------+-------+
|
|
||||||
|
|
||||||
$ openstack workflow validate create_vnfd.yaml
|
|
||||||
|
|
||||||
+-------+-------+
|
|
||||||
| Field | Value |
|
|
||||||
+-------+-------+
|
|
||||||
| Valid | True |
|
|
||||||
| Error | None |
|
|
||||||
+-------+-------+
|
|
||||||
|
|
||||||
$ openstack workflow validate delete_vnf.yaml
|
|
||||||
|
|
||||||
+-------+-------+
|
|
||||||
| Field | Value |
|
|
||||||
+-------+-------+
|
|
||||||
| Valid | True |
|
|
||||||
| Error | None |
|
|
||||||
+-------+-------+
|
|
||||||
|
|
||||||
$ openstack workflow validate delete_vnfd.yaml
|
|
||||||
|
|
||||||
+-------+-------+
|
|
||||||
| Field | Value |
|
|
||||||
+-------+-------+
|
|
||||||
| Valid | True |
|
|
||||||
| Error | None |
|
|
||||||
+-------+-------+
|
|
||||||
|
|
||||||
Registering Tacker workflows with Mistral
|
|
||||||
~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
|
|
||||||
|
|
||||||
To create std.create_vnf, std.create_vnfd, std.delete_vnfd and
|
|
||||||
std.delete_vnf workflows in Mistral.
|
|
||||||
|
|
||||||
::
|
|
||||||
|
|
||||||
usage: openstack workflow create <definition> --public
|
|
||||||
|
|
||||||
::
|
|
||||||
|
|
||||||
$ openstack workflow create create_vnf.yaml --public
|
|
||||||
|
|
||||||
+--------------------------------------+----------------+----------------------------------+--------+-------+----------------------------+------------+
|
|
||||||
| ID | Name | Project ID | Tags | Input | Created at | Updated at |
|
|
||||||
+--------------------------------------+----------------+----------------------------------+--------+-------+----------------------------+------------+
|
|
||||||
| 445e165a-3654-4996-aad4-c6fea65e95d5 | std.create_vnf | bde60e557de840a8a837733aaa96e42e | <none> | body | 2016-07-29 15:08:45.585192 | None |
|
|
||||||
+--------------------------------------+----------------+----------------------------------+--------+-------+----------------------------+------------+
|
|
||||||
|
|
||||||
$ openstack workflow create create_vnfd.yaml --public
|
|
||||||
|
|
||||||
+--------------------------------------+-----------------+----------------------------------+--------+-------+----------------------------+------------+
|
|
||||||
| ID | Name | Project ID | Tags | Input | Created at | Updated at |
|
|
||||||
+--------------------------------------+-----------------+----------------------------------+--------+-------+----------------------------+------------+
|
|
||||||
| 926caa3e-ee59-4ca0-ac1b-cae03538e389 | std.create_vnfd | bde60e557de840a8a837733aaa96e42e | <none> | body | 2016-07-29 15:08:54.933874 | None |
|
|
||||||
+--------------------------------------+-----------------+----------------------------------+--------+-------+----------------------------+------------+
|
|
||||||
|
|
||||||
$ openstack workflow create delete_vnfd.yaml --public
|
|
||||||
|
|
||||||
+--------------------------------------+-----------------+----------------------------------+--------+---------+----------------------------+------------+
|
|
||||||
| ID | Name | Project ID | Tags | Input | Created at | Updated at |
|
|
||||||
+--------------------------------------+-----------------+----------------------------------+--------+---------+----------------------------+------------+
|
|
||||||
| f15b7402-ce31-4369-98d4-818125191564 | std.delete_vnfd | bde60e557de840a8a837733aaa96e42e | <none> | vnfd_id | 2016-08-14 20:01:00.135104 | None |
|
|
||||||
+--------------------------------------+-----------------+----------------------------------+--------+---------+----------------------------+------------+
|
|
||||||
|
|
||||||
$ openstack workflow create delete_vnf.yaml --public
|
|
||||||
+--------------------------------------+----------------+----------------------------------+--------+--------+----------------------------+------------+
|
|
||||||
| ID | Name | Project ID | Tags | Input | Created at | Updated at |
|
|
||||||
+--------------------------------------+----------------+----------------------------------+--------+--------+----------------------------+------------+
|
|
||||||
| d6451b4e-6448-4a26-aa33-ac5e18c7a412 | std.delete_vnf | bde60e557de840a8a837733aaa96e42e | <none> | vnf_id | 2016-08-14 20:01:08.088654 | None |
|
|
||||||
+--------------------------------------+----------------+----------------------------------+--------+--------+----------------------------+------------+
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
VNFD resource creation with std.create_vnfd workflow
|
|
||||||
~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
|
|
||||||
To create VNFD tacker resource based on the VNFD workflow input file.
|
|
||||||
|
|
||||||
Create new execution for VNFD creation.
|
|
||||||
|
|
||||||
::
|
|
||||||
|
|
||||||
usage: openstack workflow execution create <workflow_name> [<workflow_input>] [<params>]
|
|
||||||
|
|
||||||
::
|
|
||||||
|
|
||||||
$ openstack workflow execution create std.create_vnfd create_vnfd.json
|
|
||||||
|
|
||||||
+-------------------+--------------------------------------+
|
|
||||||
| Field | Value |
|
|
||||||
+-------------------+--------------------------------------+
|
|
||||||
| ID | 31f086aa-a3c9-4f44-b8b2-bec560e32653 |
|
|
||||||
| Workflow ID | 926caa3e-ee59-4ca0-ac1b-cae03538e389 |
|
|
||||||
| Workflow name | std.create_vnfd |
|
|
||||||
| Description | |
|
|
||||||
| Task Execution ID | <none> |
|
|
||||||
| State | RUNNING |
|
|
||||||
| State info | None |
|
|
||||||
| Created at | 2016-07-29 15:11:19.485722 |
|
|
||||||
| Updated at | 2016-07-29 15:11:19.491694 |
|
|
||||||
+-------------------+--------------------------------------+
|
|
||||||
|
|
||||||
Gather execution details based on execution id.
|
|
||||||
|
|
||||||
::
|
|
||||||
|
|
||||||
usage: openstack workflow execution show <id>
|
|
||||||
|
|
||||||
::
|
|
||||||
|
|
||||||
$ openstack workflow execution show 31f086aa-a3c9-4f44-b8b2-bec560e32653
|
|
||||||
|
|
||||||
+-------------------+--------------------------------------+
|
|
||||||
| Field | Value |
|
|
||||||
+-------------------+--------------------------------------+
|
|
||||||
| ID | 31f086aa-a3c9-4f44-b8b2-bec560e32653 |
|
|
||||||
| Workflow ID | 926caa3e-ee59-4ca0-ac1b-cae03538e389 |
|
|
||||||
| Workflow name | std.create_vnfd |
|
|
||||||
| Description | |
|
|
||||||
| Task Execution ID | <none> |
|
|
||||||
| State | SUCCESS |
|
|
||||||
| State info | None |
|
|
||||||
| Created at | 2016-07-29 15:11:19 |
|
|
||||||
| Updated at | 2016-07-29 15:11:21 |
|
|
||||||
+-------------------+--------------------------------------+
|
|
||||||
|
|
||||||
.. note:: Wait until execution state become as SUCCESS.
|
|
||||||
|
|
||||||
Gather VNFD ID from execution output data.
|
|
||||||
|
|
||||||
::
|
|
||||||
|
|
||||||
usage: openstack workflow execution output show <id>
|
|
||||||
|
|
||||||
::
|
|
||||||
|
|
||||||
$ openstack workflow execution output show 31f086aa-a3c9-4f44-b8b2-bec560e32653
|
|
||||||
|
|
||||||
Response:
|
|
||||||
|
|
||||||
{
|
|
||||||
"vnfd_id": "fb164b77-5e24-402d-b5f4-c6596352cabe"
|
|
||||||
}
|
|
||||||
|
|
||||||
Verify VNFD details using OpenStackClient CLI
|
|
||||||
~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
|
|
||||||
|
|
||||||
::
|
|
||||||
|
|
||||||
$ openstack vnf descriptor show "fb164b77-5e24-402d-b5f4-c6596352cabe"
|
|
||||||
|
|
||||||
+---------------+---------------------------------------------------------------------------------------------------------------------------------------------------------------------------+
|
|
||||||
| Field | Value |
|
|
||||||
+---------------+---------------------------------------------------------------------------------------------------------------------------------------------------------------------------+
|
|
||||||
| attributes | {"vnfd": "tosca_definitions_version: tosca_simple_profile_for_nfv_1_0_0\n\ndescription: Demo example\n\nmetadata:\n template_name: sample-tosca- |
|
|
||||||
| | vnfd\n\ntopology_template:\n node_templates:\n VDU1:\n type: tosca.nodes.nfv.VDU.Tacker\n properties:\n image: cirros-0.5.2-x86_64-disk\n |
|
|
||||||
| | flavor: m1.tiny\n availability_zone: nova\n mgmt_driver: noop\n config: |\n param0: key1\n param1: key2\n\n CP1:\n type: |
|
|
||||||
| | tosca.nodes.nfv.CP.Tacker\n properties:\n management: true\n anti_spoofing_protection: false\n requirements:\n - virtualLink:\n |
|
|
||||||
| | node: VL1\n - virtualBinding:\n node: VDU1\n\n CP2:\n type: tosca.nodes.nfv.CP.Tacker\n properties:\n anti_spoofing_protection: |
|
|
||||||
| | false\n requirements:\n - virtualLink:\n node: VL2\n - virtualBinding:\n node: VDU1\n\n CP3:\n type: |
|
|
||||||
| | tosca.nodes.nfv.CP.Tacker\n properties:\n anti_spoofing_protection: false\n requirements:\n - virtualLink:\n node: VL3\n - |
|
|
||||||
| | virtualBinding:\n node: VDU1\n\n VL1:\n type: tosca.nodes.nfv.VL\n properties:\n network_name: net_mgmt\n vendor: Tacker\n\n |
|
|
||||||
| | VL2:\n type: tosca.nodes.nfv.VL\n properties:\n network_name: net0\n vendor: Tacker\n\n VL3:\n type: tosca.nodes.nfv.VL\n |
|
|
||||||
| | properties:\n network_name: net1\n vendor: Tacker\n"} |
|
|
||||||
| description | Demo example |
|
|
||||||
| id | fb164b77-5e24-402d-b5f4-c6596352cabe |
|
|
||||||
| infra_driver | openstack |
|
|
||||||
| mgmt_driver | noop |
|
|
||||||
| name | tacker-create-vnfd |
|
|
||||||
| service_types | {"service_type": "vnfd", "id": "db7c5077-7bbf-4bd3-87d5-e3c52daba255"} |
|
|
||||||
| tenant_id | bde60e557de840a8a837733aaa96e42e |
|
|
||||||
+---------------+---------------------------------------------------------------------------------------------------------------------------------------------------------------------------
|
|
||||||
|
|
||||||
VNF resource creation with std.create_vnf workflow
|
|
||||||
~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
|
|
||||||
Update the vnfd_id from the output of above execution in create_vnf.json
|
|
||||||
|
|
||||||
Create new execution for VNF creation.
|
|
||||||
|
|
||||||
::
|
|
||||||
|
|
||||||
$ openstack workflow execution create std.create_vnf create_vnf.json
|
|
||||||
|
|
||||||
+-------------------+--------------------------------------+
|
|
||||||
| Field | Value |
|
|
||||||
+-------------------+--------------------------------------+
|
|
||||||
| ID | 3bf2051b-ac2e-433b-8f18-23f57f32f184 |
|
|
||||||
| Workflow ID | 445e165a-3654-4996-aad4-c6fea65e95d5 |
|
|
||||||
| Workflow name | std.create_vnf |
|
|
||||||
| Description | |
|
|
||||||
| Task Execution ID | <none> |
|
|
||||||
| State | RUNNING |
|
|
||||||
| State info | None |
|
|
||||||
| Created at | 2016-07-29 15:16:13.066555 |
|
|
||||||
| Updated at | 2016-07-29 15:16:13.072436 |
|
|
||||||
+-------------------+--------------------------------------+
|
|
||||||
|
|
||||||
Gather execution details based on execution id.
|
|
||||||
|
|
||||||
::
|
|
||||||
|
|
||||||
$ openstack workflow execution show 3bf2051b-ac2e-433b-8f18-23f57f32f184
|
|
||||||
|
|
||||||
+-------------------+--------------------------------------+
|
|
||||||
| Field | Value |
|
|
||||||
+-------------------+--------------------------------------+
|
|
||||||
| ID | 3bf2051b-ac2e-433b-8f18-23f57f32f184 |
|
|
||||||
| Workflow ID | 445e165a-3654-4996-aad4-c6fea65e95d5 |
|
|
||||||
| Workflow name | std.create_vnf |
|
|
||||||
| Description | |
|
|
||||||
| Task Execution ID | <none> |
|
|
||||||
| State | SUCCESS |
|
|
||||||
| State info | None |
|
|
||||||
| Created at | 2016-07-29 15:16:13 |
|
|
||||||
| Updated at | 2016-07-29 15:16:45 |
|
|
||||||
+-------------------+--------------------------------------+
|
|
||||||
|
|
||||||
Gather VNF ID from execution output data.
|
|
||||||
|
|
||||||
::
|
|
||||||
|
|
||||||
$ openstack workflow execution output show 3bf2051b-ac2e-433b-8f18-23f57f32f184
|
|
||||||
|
|
||||||
Response:
|
|
||||||
|
|
||||||
{
|
|
||||||
"status": "ACTIVE",
|
|
||||||
"mgmt_ip_address": "{\"VDU1\": \"192.168.120.7\"}",
|
|
||||||
"vim_id": "22ac5ce6-1415-460c-badf-40ffc5091f94",
|
|
||||||
"vnf_id": "1c349534-a539-4d5a-b854-033f98036cd5"
|
|
||||||
}
|
|
||||||
|
|
||||||
Verify VNF details using OpenStackClient CLI
|
|
||||||
~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
|
|
||||||
::
|
|
||||||
|
|
||||||
$ openstack vnf show "1c349534-a539-4d5a-b854-033f98036cd5"
|
|
||||||
|
|
||||||
+----------------+-----------------------------------------------------------------------------------------------------------------------------------------------------------------------+
|
|
||||||
| Field | Value |
|
|
||||||
+----------------+-----------------------------------------------------------------------------------------------------------------------------------------------------------------------+
|
|
||||||
| attributes | {"heat_template": "heat_template_version: 2013-05-23\ndescription: 'Demo example\n\n '\nparameters: {}\nresources:\n VDU1:\n type: OS::Nova::Server\n |
|
|
||||||
| | properties:\n availability_zone: nova\n config_drive: false\n flavor: m1.tiny\n image: cirros-0.5.2-x86_64-disk\n networks:\n - port:\n |
|
|
||||||
| | get_resource: CP1\n - port:\n get_resource: CP2\n - port:\n get_resource: CP3\n user_data_format: SOFTWARE_CONFIG\n CP1:\n type: |
|
|
||||||
| | OS::Neutron::Port\n properties:\n network: net_mgmt\n port_security_enabled: false\n CP2:\n type: OS::Neutron::Port\n properties:\n network: |
|
|
||||||
| | net0\n port_security_enabled: false\n CP3:\n type: OS::Neutron::Port\n properties:\n network: net1\n port_security_enabled: false\noutputs:\n |
|
|
||||||
| | mgmt_ip-VDU1:\n value:\n get_attr: [CP1, fixed_ips, 0, ip_address]\n", "monitoring_policy": "{\"vdus\": {}}"} |
|
|
||||||
| description | Demo example |
|
|
||||||
| error_reason | |
|
|
||||||
| id | 1c349534-a539-4d5a-b854-033f98036cd5 |
|
|
||||||
| instance_id | 771c53df-9f41-454c-a719-7eccd3a4eba9 |
|
|
||||||
| mgmt_ip_address| {"VDU1": "192.168.120.7"} |
|
|
||||||
| name | tacker-create-vnf |
|
|
||||||
| placement_attr | {"vim_name": "VIM0"} |
|
|
||||||
| status | ACTIVE |
|
|
||||||
| tenant_id | bde60e557de840a8a837733aaa96e42e |
|
|
||||||
| vim_id | 22ac5ce6-1415-460c-badf-40ffc5091f94 |
|
|
||||||
+----------------+-----------------------------------------------------------------------------------------------------------------------------------------------------------------------+
|
|
||||||
|
|
||||||
VNF resource deletion with std.delete_vnf workflow
|
|
||||||
~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
|
|
||||||
Update the vnf_id from the output of above execution in delete_vnf.json
|
|
||||||
|
|
||||||
Create new execution for VNF deletion.
|
|
||||||
|
|
||||||
::
|
|
||||||
|
|
||||||
$ openstack workflow execution create std.delete_vnf delete_vnf.json
|
|
||||||
|
|
||||||
+-------------------+--------------------------------------+
|
|
||||||
| Field | Value |
|
|
||||||
+-------------------+--------------------------------------+
|
|
||||||
| ID | 677c7bab-18ee-4a34-b1e6-a305e98ba887 |
|
|
||||||
| Workflow ID | d6451b4e-6448-4a26-aa33-ac5e18c7a412 |
|
|
||||||
| Workflow name | std.delete_vnf |
|
|
||||||
| Description | |
|
|
||||||
| Task Execution ID | <none> |
|
|
||||||
| State | RUNNING |
|
|
||||||
| State info | None |
|
|
||||||
| Created at | 2016-08-14 20:48:00.333116 |
|
|
||||||
| Updated at | 2016-08-14 20:48:00.340124 |
|
|
||||||
+-------------------+--------------------------------------+
|
|
||||||
|
|
||||||
Gather execution details based on execution id.
|
|
||||||
|
|
||||||
::
|
|
||||||
|
|
||||||
$ openstack workflow execution show 677c7bab-18ee-4a34-b1e6-a305e98ba887
|
|
||||||
|
|
||||||
+-------------------+--------------------------------------+
|
|
||||||
| Field | Value |
|
|
||||||
+-------------------+--------------------------------------+
|
|
||||||
| ID | 677c7bab-18ee-4a34-b1e6-a305e98ba887 |
|
|
||||||
| Workflow ID | d6451b4e-6448-4a26-aa33-ac5e18c7a412 |
|
|
||||||
| Workflow name | std.delete_vnf |
|
|
||||||
| Description | |
|
|
||||||
| Task Execution ID | <none> |
|
|
||||||
| State | SUCCESS |
|
|
||||||
| State info | None |
|
|
||||||
| Created at | 2016-08-14 20:48:00 |
|
|
||||||
| Updated at | 2016-08-14 20:48:03 |
|
|
||||||
+-------------------+--------------------------------------+
|
|
||||||
|
|
||||||
|
|
||||||
Gather execution output data from execution id.
|
|
||||||
|
|
||||||
::
|
|
||||||
|
|
||||||
$ openstack workflow execution output show 677c7bab-18ee-4a34-b1e6-a305e98ba887
|
|
||||||
|
|
||||||
Response:
|
|
||||||
|
|
||||||
{
|
|
||||||
"openstack": {
|
|
||||||
"project_name": "demo",
|
|
||||||
"user_id": "f39a28fa574848dfa950b50329c1309b",
|
|
||||||
"roles": [
|
|
||||||
"anotherrole",
|
|
||||||
"Member"
|
|
||||||
],
|
|
||||||
"www_authenticate_uri": "http://192.168.122.250:5000/v3",
|
|
||||||
"auth_cacert": null,
|
|
||||||
"auth_token": "2871049fae3643ca84f44f7e17f809a0",
|
|
||||||
"is_trust_scoped": false,
|
|
||||||
"service_catalog": "[{\"endpoints\": [{\"adminURL\": \"http://192.168.122.250/identity_v2_admin\", \"region\": \"RegionOne\", \"internalURL\": \"http://192.168.122.250/identity\", \"publicURL\": \"http://192.168.122.250/identity\"}], \"type\": \"identity\", \"name\": \"keystone\"}, {\"endpoints\": [{\"adminURL\": \"http://192.168.122.250:9292\", \"region\": \"RegionOne\", \"internalURL\": \"http://192.168.122.250:9292\", \"publicURL\": \"http://192.168.122.250:9292\"}], \"type\": \"image\", \"name\": \"glance\"}, {\"endpoints\": [{\"adminURL\": \"http://192.168.122.250:8774/v2.1\", \"region\": \"RegionOne\", \"internalURL\": \"http://192.168.122.250:8774/v2.1\", \"publicURL\": \"http://192.168.122.250:8774/v2.1\"}], \"type\": \"compute\", \"name\": \"nova\"}, {\"endpoints\": [{\"adminURL\": \"http://192.168.122.250:8776/v2/bde60e557de840a8a837733aaa96e42e\", \"region\": \"RegionOne\", \"internalURL\": \"http://192.168.122.250:8776/v2/bde60e557de840a8a837733aaa96e42e\", \"publicURL\": \"http://192.168.122.250:8776/v2/bde60e557de840a8a837733aaa96e42e\"}], \"type\": \"volumev2\", \"name\": \"cinderv2\"}, {\"endpoints\": [{\"adminURL\": \"http://192.168.122.250:8776/v1/bde60e557de840a8a837733aaa96e42e\", \"region\": \"RegionOne\", \"internalURL\": \"http://192.168.122.250:8776/v1/bde60e557de840a8a837733aaa96e42e\", \"publicURL\": \"http://192.168.122.250:8776/v1/bde60e557de840a8a837733aaa96e42e\"}], \"type\": \"volume\", \"name\": \"cinder\"}, {\"endpoints\": [{\"adminURL\": \"http://192.168.122.250:9494\", \"region\": \"RegionOne\", \"internalURL\": \"http://192.168.122.250:9494\", \"publicURL\": \"http://192.168.122.250:9494\"}], \"type\": \"artifact\", \"name\": \"glare\"}, {\"endpoints\": [{\"adminURL\": \"http://192.168.122.250:8004/v1/bde60e557de840a8a837733aaa96e42e\", \"region\": \"RegionOne\", \"internalURL\": \"http://192.168.122.250:8004/v1/bde60e557de840a8a837733aaa96e42e\", \"publicURL\": \"http://192.168.122.250:8004/v1/bde60e557de840a8a837733aaa96e42e\"}], \"type\": \"orchestration\", \"name\": \"heat\"}, {\"endpoints\": [{\"adminURL\": \"http://192.168.122.250:8774/v2/bde60e557de840a8a837733aaa96e42e\", \"region\": \"RegionOne\", \"internalURL\": \"http://192.168.122.250:8774/v2/bde60e557de840a8a837733aaa96e42e\", \"publicURL\": \"http://192.168.122.250:8774/v2/bde60e557de840a8a837733aaa96e42e\"}], \"type\": \"compute_legacy\", \"name\": \"nova_legacy\"}, {\"endpoints\": [{\"adminURL\": \"http://192.168.122.250:9890/\", \"region\": \"RegionOne\", \"internalURL\": \"http://192.168.122.250:9890/\", \"publicURL\": \"http://192.168.122.250:9890/\"}], \"type\": \"nfv-orchestration\", \"name\": \"tacker\"}, {\"endpoints\": [{\"adminURL\": \"http://192.168.122.250:8989/v2\", \"region\": \"RegionOne\", \"internalURL\": \"http://192.168.122.250:8989/v2\", \"publicURL\": \"http://192.168.122.250:8989/v2\"}], \"type\": \"workflowv2\", \"name\": \"mistral\"}, {\"endpoints\": [{\"adminURL\": \"http://192.168.122.250:9696/\", \"region\": \"RegionOne\", \"internalURL\": \"http://192.168.122.250:9696/\", \"publicURL\": \"http://192.168.122.250:9696/\"}], \"type\": \"network\", \"name\": \"neutron\"}, {\"endpoints\": [{\"adminURL\": \"http://192.168.122.250:8776/v3/bde60e557de840a8a837733aaa96e42e\", \"region\": \"RegionOne\", \"internalURL\": \"http://192.168.122.250:8776/v3/bde60e557de840a8a837733aaa96e42e\", \"publicURL\": \"http://192.168.122.250:8776/v3/bde60e557de840a8a837733aaa96e42e\"}], \"type\": \"volumev3\", \"name\": \"cinderv3\"}, {\"endpoints\": [{\"adminURL\": \"http://192.168.122.250:8082\", \"region\": \"RegionOne\", \"internalURL\": \"http://192.168.122.250:8082\", \"publicURL\": \"http://192.168.122.250:8082\"}], \"type\": \"application-catalog\", \"name\": \"murano\"}, {\"endpoints\": [{\"adminURL\": \"http://192.168.122.250:8779/v1.0/bde60e557de840a8a837733aaa96e42e\", \"region\": \"RegionOne\", \"internalURL\": \"http://192.168.122.250:8779/v1.0/bde60e557de840a8a837733aaa96e42e\", \"publicURL\": \"http://192.168.122.250:8779/v1.0/bde60e557de840a8a837733aaa96e42e\"}], \"type\": \"database\", \"name\": \"trove\"}, {\"endpoints\": [{\"adminURL\": \"http://192.168.122.250:8000/v1\", \"region\": \"RegionOne\", \"internalURL\": \"http://192.168.122.250:8000/v1\", \"publicURL\": \"http://192.168.122.250:8000/v1\"}], \"type\": \"cloudformation\", \"name\": \"heat-cfn\"}]",
|
|
||||||
"project_id": "bde60e557de840a8a837733aaa96e42e",
|
|
||||||
"user_name": "demo"
|
|
||||||
},
|
|
||||||
"vnf_id": "f467e215-43a3-4083-8bbb-ce49d9c70443",
|
|
||||||
"__env": {},
|
|
||||||
"__execution": {
|
|
||||||
"input": {
|
|
||||||
"vnf_id": "f467e215-43a3-4083-8bbb-ce49d9c70443"
|
|
||||||
},
|
|
||||||
"params": {},
|
|
||||||
"id": "677c7bab-18ee-4a34-b1e6-a305e98ba887",
|
|
||||||
"spec": {
|
|
||||||
"tasks": {
|
|
||||||
"delete_vnf": {
|
|
||||||
"action": "tacker.delete_vnf vnf=<% $.vnf_id %>",
|
|
||||||
"version": "2.0",
|
|
||||||
"type": "direct",
|
|
||||||
"description": "Request to delete a VNF.",
|
|
||||||
"name": "delete_vnf"
|
|
||||||
}
|
|
||||||
},
|
|
||||||
"description": "Delete a VNF.\n",
|
|
||||||
"version": "2.0",
|
|
||||||
"input": [
|
|
||||||
"vnf_id"
|
|
||||||
],
|
|
||||||
"type": "direct",
|
|
||||||
"name": "std.delete_vnf"
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
VNFD resource deletion with std.delete_vnfd workflow
|
|
||||||
~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
|
|
||||||
Update the vnfd_id from the output of above execution in delete_vnfd.json
|
|
||||||
|
|
||||||
Create new execution for VNF deletion.
|
|
||||||
|
|
||||||
::
|
|
||||||
|
|
||||||
$ openstack workflow execution create std.delete_vnfd delete_vnfd.json
|
|
||||||
|
|
||||||
+-------------------+--------------------------------------+
|
|
||||||
| Field | Value |
|
|
||||||
+-------------------+--------------------------------------+
|
|
||||||
| ID | 1e0340c0-bee8-4ca4-8150-ac6e5eb58c99 |
|
|
||||||
| Workflow ID | f15b7402-ce31-4369-98d4-818125191564 |
|
|
||||||
| Workflow name | std.delete_vnfd |
|
|
||||||
| Description | |
|
|
||||||
| Task Execution ID | <none> |
|
|
||||||
| State | RUNNING |
|
|
||||||
| State info | None |
|
|
||||||
| Created at | 2016-08-14 20:57:06.500941 |
|
|
||||||
| Updated at | 2016-08-14 20:57:06.505780 |
|
|
||||||
+-------------------+--------------------------------------+
|
|
||||||
|
|
||||||
Gather execution details based on execution id.
|
|
||||||
|
|
||||||
::
|
|
||||||
|
|
||||||
$ openstack workflow execution show 1e0340c0-bee8-4ca4-8150-ac6e5eb58c99
|
|
||||||
|
|
||||||
+-------------------+--------------------------------------+
|
|
||||||
| Field | Value |
|
|
||||||
+-------------------+--------------------------------------+
|
|
||||||
| ID | 1e0340c0-bee8-4ca4-8150-ac6e5eb58c99 |
|
|
||||||
| Workflow ID | f15b7402-ce31-4369-98d4-818125191564 |
|
|
||||||
| Workflow name | std.delete_vnfd |
|
|
||||||
| Description | |
|
|
||||||
| Task Execution ID | <none> |
|
|
||||||
| State | SUCCESS |
|
|
||||||
| State info | None |
|
|
||||||
| Created at | 2016-08-14 20:57:06 |
|
|
||||||
| Updated at | 2016-08-14 20:57:07 |
|
|
||||||
+-------------------+--------------------------------------+
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
Gather execution output data from execution id.
|
|
||||||
|
|
||||||
::
|
|
||||||
|
|
||||||
$ openstack workflow execution output show 1e0340c0-bee8-4ca4-8150-ac6e5eb58c99
|
|
||||||
|
|
||||||
Response:
|
|
||||||
|
|
||||||
{
|
|
||||||
"openstack": {
|
|
||||||
"project_name": "demo",
|
|
||||||
"user_id": "f39a28fa574848dfa950b50329c1309b",
|
|
||||||
"roles": [
|
|
||||||
"anotherrole",
|
|
||||||
"Member"
|
|
||||||
],
|
|
||||||
"www_authenticate_uri": "http://192.168.122.250:5000/v3",
|
|
||||||
"auth_cacert": null,
|
|
||||||
"auth_token": "176c9b5ebd9d40fb9fb0a8db921609eb",
|
|
||||||
"is_trust_scoped": false,
|
|
||||||
"service_catalog": "[{\"endpoints\": [{\"adminURL\": \"http://192.168.122.250/identity_v2_admin\", \"region\": \"RegionOne\", \"internalURL\": \"http://192.168.122.250/identity\", \"publicURL\": \"http://192.168.122.250/identity\"}], \"type\": \"identity\", \"name\": \"keystone\"}, {\"endpoints\": [{\"adminURL\": \"http://192.168.122.250:9292\", \"region\": \"RegionOne\", \"internalURL\": \"http://192.168.122.250:9292\", \"publicURL\": \"http://192.168.122.250:9292\"}], \"type\": \"image\", \"name\": \"glance\"}, {\"endpoints\": [{\"adminURL\": \"http://192.168.122.250:8774/v2.1\", \"region\": \"RegionOne\", \"internalURL\": \"http://192.168.122.250:8774/v2.1\", \"publicURL\": \"http://192.168.122.250:8774/v2.1\"}], \"type\": \"compute\", \"name\": \"nova\"}, {\"endpoints\": [{\"adminURL\": \"http://192.168.122.250:8776/v2/bde60e557de840a8a837733aaa96e42e\", \"region\": \"RegionOne\", \"internalURL\": \"http://192.168.122.250:8776/v2/bde60e557de840a8a837733aaa96e42e\", \"publicURL\": \"http://192.168.122.250:8776/v2/bde60e557de840a8a837733aaa96e42e\"}], \"type\": \"volumev2\", \"name\": \"cinderv2\"}, {\"endpoints\": [{\"adminURL\": \"http://192.168.122.250:8776/v1/bde60e557de840a8a837733aaa96e42e\", \"region\": \"RegionOne\", \"internalURL\": \"http://192.168.122.250:8776/v1/bde60e557de840a8a837733aaa96e42e\", \"publicURL\": \"http://192.168.122.250:8776/v1/bde60e557de840a8a837733aaa96e42e\"}], \"type\": \"volume\", \"name\": \"cinder\"}, {\"endpoints\": [{\"adminURL\": \"http://192.168.122.250:9494\", \"region\": \"RegionOne\", \"internalURL\": \"http://192.168.122.250:9494\", \"publicURL\": \"http://192.168.122.250:9494\"}], \"type\": \"artifact\", \"name\": \"glare\"}, {\"endpoints\": [{\"adminURL\": \"http://192.168.122.250:8004/v1/bde60e557de840a8a837733aaa96e42e\", \"region\": \"RegionOne\", \"internalURL\": \"http://192.168.122.250:8004/v1/bde60e557de840a8a837733aaa96e42e\", \"publicURL\": \"http://192.168.122.250:8004/v1/bde60e557de840a8a837733aaa96e42e\"}], \"type\": \"orchestration\", \"name\": \"heat\"}, {\"endpoints\": [{\"adminURL\": \"http://192.168.122.250:8774/v2/bde60e557de840a8a837733aaa96e42e\", \"region\": \"RegionOne\", \"internalURL\": \"http://192.168.122.250:8774/v2/bde60e557de840a8a837733aaa96e42e\", \"publicURL\": \"http://192.168.122.250:8774/v2/bde60e557de840a8a837733aaa96e42e\"}], \"type\": \"compute_legacy\", \"name\": \"nova_legacy\"}, {\"endpoints\": [{\"adminURL\": \"http://192.168.122.250:9890/\", \"region\": \"RegionOne\", \"internalURL\": \"http://192.168.122.250:9890/\", \"publicURL\": \"http://192.168.122.250:9890/\"}], \"type\": \"nfv-orchestration\", \"name\": \"tacker\"}, {\"endpoints\": [{\"adminURL\": \"http://192.168.122.250:8989/v2\", \"region\": \"RegionOne\", \"internalURL\": \"http://192.168.122.250:8989/v2\", \"publicURL\": \"http://192.168.122.250:8989/v2\"}], \"type\": \"workflowv2\", \"name\": \"mistral\"}, {\"endpoints\": [{\"adminURL\": \"http://192.168.122.250:9696/\", \"region\": \"RegionOne\", \"internalURL\": \"http://192.168.122.250:9696/\", \"publicURL\": \"http://192.168.122.250:9696/\"}], \"type\": \"network\", \"name\": \"neutron\"}, {\"endpoints\": [{\"adminURL\": \"http://192.168.122.250:8776/v3/bde60e557de840a8a837733aaa96e42e\", \"region\": \"RegionOne\", \"internalURL\": \"http://192.168.122.250:8776/v3/bde60e557de840a8a837733aaa96e42e\", \"publicURL\": \"http://192.168.122.250:8776/v3/bde60e557de840a8a837733aaa96e42e\"}], \"type\": \"volumev3\", \"name\": \"cinderv3\"}, {\"endpoints\": [{\"adminURL\": \"http://192.168.122.250:8082\", \"region\": \"RegionOne\", \"internalURL\": \"http://192.168.122.250:8082\", \"publicURL\": \"http://192.168.122.250:8082\"}], \"type\": \"application-catalog\", \"name\": \"murano\"}, {\"endpoints\": [{\"adminURL\": \"http://192.168.122.250:8779/v1.0/bde60e557de840a8a837733aaa96e42e\", \"region\": \"RegionOne\", \"internalURL\": \"http://192.168.122.250:8779/v1.0/bde60e557de840a8a837733aaa96e42e\", \"publicURL\": \"http://192.168.122.250:8779/v1.0/bde60e557de840a8a837733aaa96e42e\"}], \"type\": \"database\", \"name\": \"trove\"}, {\"endpoints\": [{\"adminURL\": \"http://192.168.122.250:8000/v1\", \"region\": \"RegionOne\", \"internalURL\": \"http://192.168.122.250:8000/v1\", \"publicURL\": \"http://192.168.122.250:8000/v1\"}], \"type\": \"cloudformation\", \"name\": \"heat-cfn\"}]",
|
|
||||||
"project_id": "bde60e557de840a8a837733aaa96e42e",
|
|
||||||
"user_name": "demo"
|
|
||||||
},
|
|
||||||
"vnfd_id": "fb164b77-5e24-402d-b5f4-c6596352cabe",
|
|
||||||
"__env": {},
|
|
||||||
"__execution": {
|
|
||||||
"input": {
|
|
||||||
"vnfd_id": "fb164b77-5e24-402d-b5f4-c6596352cabe"
|
|
||||||
},
|
|
||||||
"params": {},
|
|
||||||
"id": "1e0340c0-bee8-4ca4-8150-ac6e5eb58c99",
|
|
||||||
"spec": {
|
|
||||||
"tasks": {
|
|
||||||
"delete_vnfd": {
|
|
||||||
"action": "tacker.delete_vnfd vnfd=<% $.vnfd_id %>",
|
|
||||||
"version": "2.0",
|
|
||||||
"type": "direct",
|
|
||||||
"description": "Request to delete a VNFD.",
|
|
||||||
"name": "delete_vnfd"
|
|
||||||
}
|
|
||||||
},
|
|
||||||
"description": "Delete a VNFD.\n",
|
|
||||||
"version": "2.0",
|
|
||||||
"input": [
|
|
||||||
"vnfd_id"
|
|
||||||
],
|
|
||||||
"type": "direct",
|
|
||||||
"name": "std.delete_vnfd"
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
@ -10,14 +10,6 @@ Legacy Tacker Use Cases
|
|||||||
VIM
|
VIM
|
||||||
---
|
---
|
||||||
|
|
||||||
Register
|
|
||||||
^^^^^^^^
|
|
||||||
|
|
||||||
.. toctree::
|
|
||||||
:maxdepth: 1
|
|
||||||
|
|
||||||
../contributor/tacker_vim_monitoring
|
|
||||||
|
|
||||||
Enable Multi Site
|
Enable Multi Site
|
||||||
^^^^^^^^^^^^^^^^^
|
^^^^^^^^^^^^^^^^^
|
||||||
|
|
||||||
@ -144,6 +136,5 @@ Collaboration with Other Projects
|
|||||||
|
|
||||||
../contributor/encrypt_vim_auth_with_barbican
|
../contributor/encrypt_vim_auth_with_barbican
|
||||||
../reference/block_storage_usage_guide
|
../reference/block_storage_usage_guide
|
||||||
../reference/mistral_workflows_usage_guide
|
|
||||||
alarm_monitoring_usage_guide
|
alarm_monitoring_usage_guide
|
||||||
../reference/reservation_policy_usage_guide
|
../reference/reservation_policy_usage_guide
|
||||||
|
9
releasenotes/notes/remove-mistral-5c97610e1a4140a6.yaml
Normal file
9
releasenotes/notes/remove-mistral-5c97610e1a4140a6.yaml
Normal file
@ -0,0 +1,9 @@
|
|||||||
|
---
|
||||||
|
deprecations:
|
||||||
|
- |
|
||||||
|
From 2023.1 release, dependency on Mistral has been removed from Tacker
|
||||||
|
entirely. This change removed: i) VIM monitoring; and ii) Mistral workflow
|
||||||
|
in NS API. Due to the deletion of the VIM monitoring, the status field has
|
||||||
|
been removed from the VIM table and VIM status in the response will be
|
||||||
|
filled by a dummy value. This field will be completely removed in the next
|
||||||
|
release
|
@ -40,7 +40,6 @@ openstacksdk>=0.44.0 # Apache-2.0
|
|||||||
python-barbicanclient>=4.5.2 # Apache-2.0
|
python-barbicanclient>=4.5.2 # Apache-2.0
|
||||||
python-heatclient>=1.10.0 # Apache-2.0
|
python-heatclient>=1.10.0 # Apache-2.0
|
||||||
python-keystoneclient>=3.8.0 # Apache-2.0
|
python-keystoneclient>=3.8.0 # Apache-2.0
|
||||||
python-mistralclient>=4.2.0 # Apache-2.0
|
|
||||||
python-neutronclient>=6.7.0 # Apache-2.0
|
python-neutronclient>=6.7.0 # Apache-2.0
|
||||||
python-novaclient>=9.1.0 # Apache-2.0
|
python-novaclient>=9.1.0 # Apache-2.0
|
||||||
python-tackerclient>=1.11.0 # Apache-2.0
|
python-tackerclient>=1.11.0 # Apache-2.0
|
||||||
|
@ -103,9 +103,6 @@ oslo.config.opts =
|
|||||||
tacker.vnfm.plugin = tacker.vnfm.plugin:config_opts
|
tacker.vnfm.plugin = tacker.vnfm.plugin:config_opts
|
||||||
tacker.wsgi = tacker.wsgi:config_opts
|
tacker.wsgi = tacker.wsgi:config_opts
|
||||||
|
|
||||||
mistral.actions =
|
|
||||||
tacker.vim_ping_action = tacker.nfvo.workflows.vim_monitor.vim_ping_action:PingVimAction
|
|
||||||
|
|
||||||
oslo.policy.enforcer =
|
oslo.policy.enforcer =
|
||||||
tacker = tacker.policy:get_enforcer
|
tacker = tacker.policy:get_enforcer
|
||||||
|
|
||||||
|
@ -24,7 +24,6 @@ class OpenstackClients(object):
|
|||||||
super(OpenstackClients, self).__init__()
|
super(OpenstackClients, self).__init__()
|
||||||
self.keystone_plugin = keystone.Keystone()
|
self.keystone_plugin = keystone.Keystone()
|
||||||
self.heat_client = None
|
self.heat_client = None
|
||||||
self.mistral_client = None
|
|
||||||
self.keystone_client = None
|
self.keystone_client = None
|
||||||
self.region_name = region_name
|
self.region_name = region_name
|
||||||
|
|
||||||
|
@ -10,7 +10,6 @@
|
|||||||
# License for the specific language governing permissions and limitations
|
# License for the specific language governing permissions and limitations
|
||||||
# under the License.
|
# under the License.
|
||||||
|
|
||||||
import ast
|
|
||||||
from datetime import datetime
|
from datetime import datetime
|
||||||
|
|
||||||
from oslo_db.exception import DBDuplicateEntry
|
from oslo_db.exception import DBDuplicateEntry
|
||||||
@ -292,27 +291,11 @@ class NSPluginDb(network_service.NSPluginBase, db_base.CommonDbMixin):
|
|||||||
details=evt_details)
|
details=evt_details)
|
||||||
return self._make_ns_dict(ns_db)
|
return self._make_ns_dict(ns_db)
|
||||||
|
|
||||||
def create_ns_post(self, context, ns_id, mistral_obj,
|
def create_ns_post(self, context, ns_id, vnfd_dict, vnffgd_templates):
|
||||||
vnfd_dict, vnffgd_templates, error_reason):
|
|
||||||
LOG.debug('ns ID %s', ns_id)
|
LOG.debug('ns ID %s', ns_id)
|
||||||
output = ast.literal_eval(mistral_obj.output)
|
|
||||||
mgmt_ip_addresses = dict()
|
mgmt_ip_addresses = dict()
|
||||||
vnf_ids = dict()
|
vnf_ids = dict()
|
||||||
vnffg_ids = dict()
|
vnffg_ids = dict()
|
||||||
if len(output) > 0:
|
|
||||||
for vnfd_name, vnfd_val in vnfd_dict.items():
|
|
||||||
for instance in vnfd_val['instances']:
|
|
||||||
if 'mgmt_ip_address_' + instance in output:
|
|
||||||
mgmt_ip_addresses[instance] = ast.literal_eval(
|
|
||||||
output['mgmt_ip_address_' + instance].strip())
|
|
||||||
vnf_ids[instance] = output['vnf_id_' + instance]
|
|
||||||
vnf_ids = str(vnf_ids)
|
|
||||||
mgmt_ip_addresses = str(mgmt_ip_addresses)
|
|
||||||
if vnffgd_templates:
|
|
||||||
for vnffg_name in vnffgd_templates:
|
|
||||||
vnffg_output = 'vnffg_id_%s' % vnffg_name
|
|
||||||
vnffg_ids[vnffg_name] = output[vnffg_output]
|
|
||||||
vnffg_ids = str(vnffg_ids)
|
|
||||||
|
|
||||||
if not vnf_ids:
|
if not vnf_ids:
|
||||||
vnf_ids = None
|
vnf_ids = None
|
||||||
@ -320,8 +303,7 @@ class NSPluginDb(network_service.NSPluginBase, db_base.CommonDbMixin):
|
|||||||
mgmt_ip_addresses = None
|
mgmt_ip_addresses = None
|
||||||
if not vnffg_ids:
|
if not vnffg_ids:
|
||||||
vnffg_ids = None
|
vnffg_ids = None
|
||||||
status = constants.ACTIVE if mistral_obj.state == 'SUCCESS' \
|
status = constants.ACTIVE
|
||||||
else constants.ERROR
|
|
||||||
|
|
||||||
with context.session.begin(subtransactions=True):
|
with context.session.begin(subtransactions=True):
|
||||||
ns_db = self._get_resource(context, NS, ns_id)
|
ns_db = self._get_resource(context, NS, ns_id)
|
||||||
@ -329,7 +311,6 @@ class NSPluginDb(network_service.NSPluginBase, db_base.CommonDbMixin):
|
|||||||
ns_db.update({'vnffg_ids': vnffg_ids})
|
ns_db.update({'vnffg_ids': vnffg_ids})
|
||||||
ns_db.update({'mgmt_ip_addresses': mgmt_ip_addresses})
|
ns_db.update({'mgmt_ip_addresses': mgmt_ip_addresses})
|
||||||
ns_db.update({'status': status})
|
ns_db.update({'status': status})
|
||||||
ns_db.update({'error_reason': error_reason})
|
|
||||||
ns_db.update({'updated_at': timeutils.utcnow()})
|
ns_db.update({'updated_at': timeutils.utcnow()})
|
||||||
ns_dict = self._make_ns_dict(ns_db)
|
ns_dict = self._make_ns_dict(ns_db)
|
||||||
|
|
||||||
@ -362,8 +343,8 @@ class NSPluginDb(network_service.NSPluginBase, db_base.CommonDbMixin):
|
|||||||
tstamp=timeutils.utcnow(), details="NS delete initiated")
|
tstamp=timeutils.utcnow(), details="NS delete initiated")
|
||||||
return deleted_ns_db
|
return deleted_ns_db
|
||||||
|
|
||||||
def delete_ns_post(self, context, ns_id, mistral_obj,
|
def delete_ns_post(self, context, ns_id, soft_delete=True,
|
||||||
error_reason, soft_delete=True, force_delete=False):
|
force_delete=False):
|
||||||
ns = self.get_ns(context, ns_id)
|
ns = self.get_ns(context, ns_id)
|
||||||
nsd_id = ns.get('nsd_id')
|
nsd_id = ns.get('nsd_id')
|
||||||
with context.session.begin(subtransactions=True):
|
with context.session.begin(subtransactions=True):
|
||||||
@ -376,17 +357,6 @@ class NSPluginDb(network_service.NSPluginBase, db_base.CommonDbMixin):
|
|||||||
self._model_query(context, NS).
|
self._model_query(context, NS).
|
||||||
filter(NS.id == ns_id).
|
filter(NS.id == ns_id).
|
||||||
filter(NS.status == constants.PENDING_DELETE))
|
filter(NS.status == constants.PENDING_DELETE))
|
||||||
if not force_delete and (mistral_obj
|
|
||||||
and mistral_obj.state == 'ERROR'):
|
|
||||||
query.update({'status': constants.ERROR})
|
|
||||||
self._cos_db_plg.create_event(
|
|
||||||
context, res_id=ns_id,
|
|
||||||
res_type=constants.RES_TYPE_NS,
|
|
||||||
res_state=constants.ERROR,
|
|
||||||
evt_type=constants.RES_EVT_DELETE,
|
|
||||||
tstamp=timeutils.utcnow(),
|
|
||||||
details="NS Delete ERROR")
|
|
||||||
else:
|
|
||||||
if soft_delete:
|
if soft_delete:
|
||||||
deleted_time_stamp = timeutils.utcnow()
|
deleted_time_stamp = timeutils.utcnow()
|
||||||
query.update({'deleted_at': deleted_time_stamp})
|
query.update({'deleted_at': deleted_time_stamp})
|
||||||
|
@ -1,27 +0,0 @@
|
|||||||
# Licensed under the Apache License, Version 2.0 (the "License"); you may
|
|
||||||
# not use this file except in compliance with the License. You may obtain
|
|
||||||
# a copy of the License at
|
|
||||||
#
|
|
||||||
# http://www.apache.org/licenses/LICENSE-2.0
|
|
||||||
#
|
|
||||||
# Unless required by applicable law or agreed to in writing, software
|
|
||||||
# distributed under the License is distributed on an "AS IS" BASIS, WITHOUT
|
|
||||||
# WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the
|
|
||||||
# License for the specific language governing permissions and limitations
|
|
||||||
# under the License.
|
|
||||||
|
|
||||||
from mistralclient.api import client as mistral_client
|
|
||||||
|
|
||||||
|
|
||||||
class MistralClient(object):
|
|
||||||
"""Mistral Client class for NSD"""
|
|
||||||
|
|
||||||
def __init__(self, keystone, auth_token):
|
|
||||||
endpoint = keystone.get_endpoint(
|
|
||||||
service_type='workflowv2', region_name=None)
|
|
||||||
|
|
||||||
self.client = mistral_client.client(auth_token=auth_token,
|
|
||||||
mistral_url=endpoint)
|
|
||||||
|
|
||||||
def get_client(self):
|
|
||||||
return self.client
|
|
@ -1,36 +0,0 @@
|
|||||||
# Licensed under the Apache License, Version 2.0 (the "License"); you may
|
|
||||||
# not use this file except in compliance with the License. You may obtain
|
|
||||||
# a copy of the License at
|
|
||||||
#
|
|
||||||
# http://www.apache.org/licenses/LICENSE-2.0
|
|
||||||
#
|
|
||||||
# Unless required by applicable law or agreed to in writing, software
|
|
||||||
# distributed under the License is distributed on an "AS IS" BASIS, WITHOUT
|
|
||||||
# WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the
|
|
||||||
# License for the specific language governing permissions and limitations
|
|
||||||
# under the License.
|
|
||||||
|
|
||||||
from oslo_utils import uuidutils
|
|
||||||
|
|
||||||
|
|
||||||
class WorkflowGeneratorBase(object):
|
|
||||||
def __init__(self, resource, action):
|
|
||||||
self.resource = resource
|
|
||||||
self.action = action
|
|
||||||
self.wf_name = self.action + '_' + self.resource
|
|
||||||
self.wf_identifier = 'std.' + self.wf_name + uuidutils.generate_uuid()
|
|
||||||
self.task = getattr(self, self.wf_name)
|
|
||||||
self.input_dict = dict()
|
|
||||||
self._build_basic_workflow()
|
|
||||||
|
|
||||||
def _build_basic_workflow(self):
|
|
||||||
self.definition = {
|
|
||||||
'version': '2.0',
|
|
||||||
self.wf_identifier: {
|
|
||||||
'type': 'direct',
|
|
||||||
'input': [self.resource]
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
def get_tasks(self):
|
|
||||||
return self.definition[self.wf_identifier].get('tasks')
|
|
@ -15,7 +15,6 @@
|
|||||||
# under the License.
|
# under the License.
|
||||||
|
|
||||||
import os
|
import os
|
||||||
import yaml
|
|
||||||
|
|
||||||
from keystoneauth1 import exceptions
|
from keystoneauth1 import exceptions
|
||||||
from keystoneauth1 import identity
|
from keystoneauth1 import identity
|
||||||
@ -32,10 +31,8 @@ from tacker.common import utils
|
|||||||
from tacker import context as t_context
|
from tacker import context as t_context
|
||||||
from tacker.extensions import nfvo
|
from tacker.extensions import nfvo
|
||||||
from tacker.keymgr import API as KEYMGR_API
|
from tacker.keymgr import API as KEYMGR_API
|
||||||
from tacker.mistral import mistral_client
|
|
||||||
from tacker.nfvo.drivers.vim import abstract_vim_driver
|
from tacker.nfvo.drivers.vim import abstract_vim_driver
|
||||||
from tacker.nfvo.drivers.vnffg import abstract_vnffg_driver
|
from tacker.nfvo.drivers.vnffg import abstract_vnffg_driver
|
||||||
from tacker.nfvo.drivers.workflow import workflow_generator
|
|
||||||
from tacker.nfvo.nfvo_plugin import NfvoPlugin
|
from tacker.nfvo.nfvo_plugin import NfvoPlugin
|
||||||
from tacker.plugins.common import constants
|
from tacker.plugins.common import constants
|
||||||
from tacker.vnfm import keystone
|
from tacker.vnfm import keystone
|
||||||
@ -707,46 +704,6 @@ class OpenStack_Driver(abstract_vim_driver.VimAbstractDriver,
|
|||||||
neutronclient_ = NeutronClient(auth_attr)
|
neutronclient_ = NeutronClient(auth_attr)
|
||||||
neutronclient_.flow_classifier_delete(fc_id)
|
neutronclient_.flow_classifier_delete(fc_id)
|
||||||
|
|
||||||
def get_mistral_client(self, auth_dict):
|
|
||||||
if not auth_dict:
|
|
||||||
LOG.warning("auth dict required to instantiate mistral client")
|
|
||||||
raise EnvironmentError('auth dict required for'
|
|
||||||
' mistral workflow driver')
|
|
||||||
return mistral_client.MistralClient(
|
|
||||||
keystone.Keystone().initialize_client(**auth_dict),
|
|
||||||
auth_dict['token']).get_client()
|
|
||||||
|
|
||||||
def prepare_and_create_workflow(self, resource, action,
|
|
||||||
kwargs, auth_dict=None):
|
|
||||||
mistral_client = self.get_mistral_client(auth_dict)
|
|
||||||
wg = workflow_generator.WorkflowGenerator(resource, action)
|
|
||||||
wg.task(**kwargs)
|
|
||||||
if not wg.get_tasks():
|
|
||||||
raise nfvo.NoTasksException(resource=resource, action=action)
|
|
||||||
yaml.SafeDumper.ignore_aliases = lambda self, data: True
|
|
||||||
definition_yaml = yaml.safe_dump(wg.definition)
|
|
||||||
workflow = mistral_client.workflows.create(definition_yaml)
|
|
||||||
return {'id': workflow[0].id, 'input': wg.get_input_dict()}
|
|
||||||
|
|
||||||
def execute_workflow(self, workflow, auth_dict=None):
|
|
||||||
return self.get_mistral_client(auth_dict) \
|
|
||||||
.executions.create(
|
|
||||||
workflow_identifier=workflow['id'],
|
|
||||||
workflow_input=workflow['input'],
|
|
||||||
wf_params={})
|
|
||||||
|
|
||||||
def get_execution(self, execution_id, auth_dict=None):
|
|
||||||
return self.get_mistral_client(auth_dict) \
|
|
||||||
.executions.get(execution_id)
|
|
||||||
|
|
||||||
def delete_execution(self, execution_id, auth_dict=None):
|
|
||||||
return self.get_mistral_client(auth_dict).executions \
|
|
||||||
.delete(execution_id, force=True)
|
|
||||||
|
|
||||||
def delete_workflow(self, workflow_id, auth_dict=None):
|
|
||||||
return self.get_mistral_client(auth_dict) \
|
|
||||||
.workflows.delete(workflow_id)
|
|
||||||
|
|
||||||
def _delete_ppgs_and_pps(self, neutronclient, new_ppgs,
|
def _delete_ppgs_and_pps(self, neutronclient, new_ppgs,
|
||||||
past_ppgs_dict, pcs_list, fc_ids):
|
past_ppgs_dict, pcs_list, fc_ids):
|
||||||
if new_ppgs:
|
if new_ppgs:
|
||||||
|
@ -1,277 +0,0 @@
|
|||||||
# Licensed under the Apache License, Version 2.0 (the "License"); you may
|
|
||||||
# not use this file except in compliance with the License. You may obtain
|
|
||||||
# a copy of the License at
|
|
||||||
#
|
|
||||||
# http://www.apache.org/licenses/LICENSE-2.0
|
|
||||||
#
|
|
||||||
# Unless required by applicable law or agreed to in writing, software
|
|
||||||
# distributed under the License is distributed on an "AS IS" BASIS, WITHOUT
|
|
||||||
# WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the
|
|
||||||
# License for the specific language governing permissions and limitations
|
|
||||||
# under the License.
|
|
||||||
|
|
||||||
import ast
|
|
||||||
|
|
||||||
from tacker.mistral import workflow_generator
|
|
||||||
|
|
||||||
|
|
||||||
OUTPUT = {
|
|
||||||
'create_vnf': ['vnf_id', 'vim_id', 'mgmt_ip_address', 'status'],
|
|
||||||
'create_vnffg': ['vnffg_id'],
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
class WorkflowGenerator(workflow_generator.WorkflowGeneratorBase):
|
|
||||||
|
|
||||||
def _add_create_vnf_tasks(self, ns):
|
|
||||||
vnfds = ns['vnfd_details']
|
|
||||||
task_dict = dict()
|
|
||||||
for vnfd_name, vnfd_info in (vnfds).items():
|
|
||||||
nodes = vnfd_info['instances']
|
|
||||||
for node in nodes:
|
|
||||||
task = self.wf_name + '_' + node
|
|
||||||
task_dict[task] = {
|
|
||||||
'action': 'tacker.create_vnf body=<% $.ns.{0} '
|
|
||||||
'%>'.format(node),
|
|
||||||
'input': {'body': '<% $.ns.{0} %>'.format(node)},
|
|
||||||
'publish': {
|
|
||||||
'vnf_id_' + node: '<% task({0}).result.vnf.id '
|
|
||||||
'%>'.format(task),
|
|
||||||
'vim_id_' + node: '<% task({0}).result.vnf.vim_id'
|
|
||||||
' %>'.format(task),
|
|
||||||
'mgmt_ip_address_' + node: '<% task({0}).result.vnf.'
|
|
||||||
'mgmt_ip_address '
|
|
||||||
'%>'.format(task),
|
|
||||||
'status_' + node: '<% task({0}).result.vnf.status'
|
|
||||||
' %>'.format(task),
|
|
||||||
},
|
|
||||||
'on-success': ['wait_vnf_active_%s' % node]
|
|
||||||
}
|
|
||||||
return task_dict
|
|
||||||
|
|
||||||
def _add_wait_vnf_tasks(self, ns):
|
|
||||||
vnfds = ns['vnfd_details']
|
|
||||||
task_dict = dict()
|
|
||||||
for vnfd_name, vnfd_info in (vnfds).items():
|
|
||||||
nodes = vnfd_info['instances']
|
|
||||||
for node in nodes:
|
|
||||||
task = 'wait_vnf_active_%s' % node
|
|
||||||
task_dict[task] = {
|
|
||||||
'action': 'tacker.show_vnf vnf=<% $.vnf_id_{0} '
|
|
||||||
'%>'.format(node),
|
|
||||||
'retry': {
|
|
||||||
'count': 10,
|
|
||||||
'delay': 10,
|
|
||||||
'break-on': '<% $.status_{0} = "ERROR"'
|
|
||||||
' %>'.format(node),
|
|
||||||
'continue-on': '<% $.status_{0} = "PENDING_CREATE" '
|
|
||||||
'%>'.format(node),
|
|
||||||
},
|
|
||||||
'publish': {
|
|
||||||
'mgmt_ip_address_' + node: ' <% task({0}).result.'
|
|
||||||
'vnf.mgmt_ip_address '
|
|
||||||
'%>'.format(task),
|
|
||||||
'status_' + node: '<% task({0}).result.vnf.status'
|
|
||||||
' %>'.format(task),
|
|
||||||
},
|
|
||||||
'on-success': [
|
|
||||||
{'delete_vnf_' + node: '<% $.status_{0}='
|
|
||||||
'"ERROR" %>'.format(node)}
|
|
||||||
]
|
|
||||||
}
|
|
||||||
vnffgd_templates = ns.get('vnffgd_templates')
|
|
||||||
if vnffgd_templates:
|
|
||||||
for vnffg_name in vnffgd_templates:
|
|
||||||
vnffg_group = vnffgd_templates[vnffg_name][
|
|
||||||
'topology_template']['groups'][vnffg_name]
|
|
||||||
constituent_vnfs = vnffg_group[
|
|
||||||
'properties']['constituent_vnfs']
|
|
||||||
|
|
||||||
if vnfd_name in constituent_vnfs:
|
|
||||||
task_dict[task]['on-success'].append(
|
|
||||||
'create_vnffg_%s' % vnffg_name)
|
|
||||||
return task_dict
|
|
||||||
|
|
||||||
def _add_delete_vnf_tasks(self, ns, vnffg_ids=None):
|
|
||||||
vnfds = ns['vnfd_details']
|
|
||||||
vnf_attr = {'vnf': {'attributes': {
|
|
||||||
'force': ns.get('force_delete', False)}}}
|
|
||||||
task_dict = dict()
|
|
||||||
for vnfd_name, vnfd_info in (vnfds).items():
|
|
||||||
nodes = vnfd_info['instances']
|
|
||||||
for node in nodes:
|
|
||||||
task = 'delete_vnf_%s' % node
|
|
||||||
task_dict[task] = {
|
|
||||||
'action': 'tacker.delete_vnf vnf=<% $.vnf_id_{0}'
|
|
||||||
'%>'.format(node),
|
|
||||||
'input': {'body': vnf_attr},
|
|
||||||
}
|
|
||||||
if vnffg_ids and len(vnffg_ids):
|
|
||||||
task_dict[task].update({'join': 'all'})
|
|
||||||
return task_dict
|
|
||||||
|
|
||||||
def _add_create_vnffg_task(self, vnffgd_templates):
|
|
||||||
task_dict = dict()
|
|
||||||
previous_task = None
|
|
||||||
for vnffg_name in vnffgd_templates:
|
|
||||||
task = 'create_vnffg_%s' % vnffg_name
|
|
||||||
vnffg_output = 'vnffg_id_%s' % vnffg_name
|
|
||||||
task_dict[task] = {
|
|
||||||
'join': 'all',
|
|
||||||
'action': 'tacker.create_vnffg body=<% $.ns.{0} '
|
|
||||||
'%>'.format(vnffg_name),
|
|
||||||
'input': {'body': '<% $.ns.{0} %>'.format(vnffg_name)},
|
|
||||||
'publish': {
|
|
||||||
vnffg_output: '<% task({0}).result.'
|
|
||||||
'vnffg.id %>'.format(task)}
|
|
||||||
}
|
|
||||||
if previous_task:
|
|
||||||
task_dict[previous_task].update({'on-success': [task]})
|
|
||||||
previous_task = task
|
|
||||||
return task_dict
|
|
||||||
|
|
||||||
def _add_delete_vnffg_task(self, ns):
|
|
||||||
task_dict = dict()
|
|
||||||
vnfds = ns['vnfd_details']
|
|
||||||
vnffg_ids = ns['vnffg_details']
|
|
||||||
delayed_tasks = list()
|
|
||||||
|
|
||||||
for vnfd_name, vnfd_info in (vnfds).items():
|
|
||||||
nodes = vnfd_info['instances']
|
|
||||||
for node in nodes:
|
|
||||||
wait_task = 'delete_vnf_%s' % node
|
|
||||||
delayed_tasks.append(wait_task)
|
|
||||||
|
|
||||||
previous_task = None
|
|
||||||
for vnffg_name in vnffg_ids:
|
|
||||||
task = 'delete_vnffg_%s' % vnffg_name
|
|
||||||
if previous_task:
|
|
||||||
wait_tasks = delayed_tasks + [previous_task]
|
|
||||||
else:
|
|
||||||
wait_tasks = delayed_tasks
|
|
||||||
previous_task = task
|
|
||||||
task_dict[task] = {
|
|
||||||
'action': 'tacker.delete_vnffg vnffg=<% $.{0} '
|
|
||||||
'%>'.format(vnffg_name),
|
|
||||||
'on-success': wait_tasks
|
|
||||||
}
|
|
||||||
return task_dict
|
|
||||||
|
|
||||||
def _build_output_dict(self, ns):
|
|
||||||
vnfds = ns['vnfd_details']
|
|
||||||
task_dict = dict()
|
|
||||||
for vnfd_name, vnfd_info in (vnfds).items():
|
|
||||||
nodes = vnfd_info['instances']
|
|
||||||
for node in nodes:
|
|
||||||
for op_name in OUTPUT['create_vnf']:
|
|
||||||
task_dict[op_name + '_' + node] = \
|
|
||||||
'<% $.{0}_{1} %>'.format(op_name, node)
|
|
||||||
vnffgd_templates = ns.get('vnffgd_templates')
|
|
||||||
if vnffgd_templates:
|
|
||||||
for vnffg_name in vnffgd_templates:
|
|
||||||
for op_name in OUTPUT['create_vnffg']:
|
|
||||||
vnffg_output = '%s_%s' % (op_name, vnffg_name)
|
|
||||||
task_dict[vnffg_output] = \
|
|
||||||
'<% $.{0}_{1} %>'.format(op_name, vnffg_name)
|
|
||||||
return task_dict
|
|
||||||
|
|
||||||
def get_input_dict(self):
|
|
||||||
return self.input_dict
|
|
||||||
|
|
||||||
def build_input(self, ns, params):
|
|
||||||
vnfds = ns['vnfd_details']
|
|
||||||
ns_id = ns['ns'].get('ns_id')
|
|
||||||
ns_name = ns['ns'].get('name')
|
|
||||||
self.input_dict = {'ns': {}}
|
|
||||||
for vnfd_name, vnfd_info in (vnfds).items():
|
|
||||||
nodes = vnfd_info['instances']
|
|
||||||
for node in nodes:
|
|
||||||
vnf_name = '%s_VNF_%s' % (ns_name, vnfd_info['id'])
|
|
||||||
self.input_dict['ns'][node] = dict()
|
|
||||||
self.input_dict['ns'][node]['vnf'] = {
|
|
||||||
'attributes': {},
|
|
||||||
'vim_id': ns['ns'].get('vim_id', ''),
|
|
||||||
'vnfd_id': vnfd_info['id'],
|
|
||||||
'name': vnf_name
|
|
||||||
}
|
|
||||||
if params.get(vnfd_name):
|
|
||||||
self.input_dict['ns'][node]['vnf']['attributes'] = {
|
|
||||||
'param_values': params.get(vnfd_name)
|
|
||||||
}
|
|
||||||
if ns.get('vnffgd_templates'):
|
|
||||||
vnffg_input = self.build_vnffg_input(ns, params, ns_id)
|
|
||||||
self.input_dict['ns'].update(vnffg_input)
|
|
||||||
|
|
||||||
def build_vnffg_input(self, ns, params, ns_id):
|
|
||||||
vnffgd_templates = ns.get('vnffgd_templates')
|
|
||||||
vnffg_input = dict()
|
|
||||||
for vnffg_name in vnffgd_templates:
|
|
||||||
vnffg_group = vnffgd_templates[vnffg_name][
|
|
||||||
'topology_template']['groups'][vnffg_name]
|
|
||||||
constituent_vnfs = vnffg_group[
|
|
||||||
'properties']['constituent_vnfs']
|
|
||||||
vnf_mapping = self.get_vnf_mapping(ns, constituent_vnfs)
|
|
||||||
vnffgd_body = dict()
|
|
||||||
vnffgd_body['vnffg'] = {
|
|
||||||
'name': '%s_%s_%s' % (ns['ns'].get('name'), vnffg_name, ns_id),
|
|
||||||
'vnffgd_template': vnffgd_templates[vnffg_name],
|
|
||||||
'vnf_mapping': vnf_mapping,
|
|
||||||
'attributes': {
|
|
||||||
'param_values': params.get('nsd')},
|
|
||||||
'ns_id': ns_id
|
|
||||||
}
|
|
||||||
vnffg_input[vnffg_name] = vnffgd_body
|
|
||||||
return vnffg_input
|
|
||||||
|
|
||||||
def get_vnf_mapping(self, ns, constituent_vnfs):
|
|
||||||
vnfds = ns['vnfd_details']
|
|
||||||
vnf_mapping = dict()
|
|
||||||
for vnfd_name, vnfd_info in (vnfds).items():
|
|
||||||
if vnfd_name in constituent_vnfs:
|
|
||||||
vnf_name = '%s_VNF_%s' % (ns['ns'].get('name'),
|
|
||||||
vnfd_info['id'])
|
|
||||||
vnf_mapping[vnfd_name] = vnf_name
|
|
||||||
return vnf_mapping
|
|
||||||
|
|
||||||
def create_ns(self, **kwargs):
|
|
||||||
ns = kwargs.get('ns')
|
|
||||||
params = kwargs.get('params')
|
|
||||||
|
|
||||||
tasks = {}
|
|
||||||
for func in [self._add_create_vnf_tasks,
|
|
||||||
self._add_wait_vnf_tasks,
|
|
||||||
self._add_delete_vnf_tasks]:
|
|
||||||
tasks.update(func(ns))
|
|
||||||
|
|
||||||
self.build_input(ns, params)
|
|
||||||
vnffgd_templates = ns.get('vnffgd_templates')
|
|
||||||
if vnffgd_templates:
|
|
||||||
create_task = self._add_create_vnffg_task(vnffgd_templates)
|
|
||||||
tasks.update(create_task)
|
|
||||||
|
|
||||||
self.definition[self.wf_identifier]['tasks'] = tasks
|
|
||||||
self.definition[self.wf_identifier]['output'] = \
|
|
||||||
self._build_output_dict(ns)
|
|
||||||
|
|
||||||
def delete_ns(self, ns):
|
|
||||||
ns_dict = {'vnfd_details': {}}
|
|
||||||
vnf_ids = ast.literal_eval(ns['vnf_ids'])
|
|
||||||
self.definition[self.wf_identifier]['input'] = []
|
|
||||||
for vnf in vnf_ids:
|
|
||||||
vnf_key = 'vnf_id_' + vnf
|
|
||||||
self.definition[self.wf_identifier]['input'].append(vnf_key)
|
|
||||||
self.input_dict[vnf_key] = vnf_ids[vnf]
|
|
||||||
ns_dict['vnfd_details'][vnf] = {'instances': [vnf]}
|
|
||||||
self.definition[self.wf_identifier]['tasks'] = dict()
|
|
||||||
|
|
||||||
vnffg_ids = ast.literal_eval(ns.get('vnffg_ids'))
|
|
||||||
if len(vnffg_ids):
|
|
||||||
for vnffg_name in vnffg_ids:
|
|
||||||
self.definition[self.wf_identifier]['input'].append(vnffg_name)
|
|
||||||
self.input_dict[vnffg_name] = vnffg_ids[vnffg_name]
|
|
||||||
ns_dict['vnffg_details'] = vnffg_ids
|
|
||||||
self.definition[self.wf_identifier]['tasks'].update(
|
|
||||||
self._add_delete_vnffg_task(ns_dict))
|
|
||||||
ns_dict['force_delete'] = ns.get('force_delete', False)
|
|
||||||
self.definition[self.wf_identifier]['tasks'].update(
|
|
||||||
self._add_delete_vnf_tasks(ns_dict, vnffg_ids))
|
|
@ -16,7 +16,6 @@
|
|||||||
|
|
||||||
import copy
|
import copy
|
||||||
import os
|
import os
|
||||||
import time
|
|
||||||
import yaml
|
import yaml
|
||||||
|
|
||||||
from cryptography import fernet
|
from cryptography import fernet
|
||||||
@ -51,8 +50,6 @@ from toscaparser import tosca_template
|
|||||||
|
|
||||||
LOG = logging.getLogger(__name__)
|
LOG = logging.getLogger(__name__)
|
||||||
CONF = cfg.CONF
|
CONF = cfg.CONF
|
||||||
MISTRAL_RETRIES = 30
|
|
||||||
MISTRAL_RETRY_WAIT = 6
|
|
||||||
|
|
||||||
|
|
||||||
def config_opts():
|
def config_opts():
|
||||||
@ -719,17 +716,12 @@ class NfvoPlugin(nfvo_db_plugin.NfvoPluginDb, vnffg_db.VnffgPluginDbMixin,
|
|||||||
vnffgd_templates[vnffg_name] = vnffgd_template
|
vnffgd_templates[vnffg_name] = vnffgd_template
|
||||||
return vnffgd_templates
|
return vnffgd_templates
|
||||||
|
|
||||||
|
# TODO(hiromu): Remove create NS API after the deprecation is accepted.
|
||||||
@log.log
|
@log.log
|
||||||
def create_ns(self, context, ns):
|
def create_ns(self, context, ns):
|
||||||
"""Create NS, corresponding VNFs, VNFFGs.
|
"""Create NS, corresponding VNFs, VNFFGs.
|
||||||
|
|
||||||
:param ns: ns dict which contains nsd_id and attributes
|
:param ns: ns dict which contains nsd_id and attributes
|
||||||
This method has 3 steps:
|
|
||||||
step-1: substitute all get_input params to its corresponding values
|
|
||||||
step-2: Build params dict for substitution mappings case through which
|
|
||||||
VNFs will actually substitute their requirements.
|
|
||||||
step-3: Create mistral workflow to create VNFs, VNFFG and execute the
|
|
||||||
workflow
|
|
||||||
"""
|
"""
|
||||||
ns_info = ns['ns']
|
ns_info = ns['ns']
|
||||||
name = ns_info['name']
|
name = ns_info['name']
|
||||||
@ -753,7 +745,6 @@ class NfvoPlugin(nfvo_db_plugin.NfvoPluginDb, vnffg_db.VnffgPluginDbMixin,
|
|||||||
|
|
||||||
vim_res = self.vim_client.get_vim(context, ns['ns']['vim_id'],
|
vim_res = self.vim_client.get_vim(context, ns['ns']['vim_id'],
|
||||||
region_name)
|
region_name)
|
||||||
driver_type = vim_res['vim_type']
|
|
||||||
if not ns['ns']['vim_id']:
|
if not ns['ns']['vim_id']:
|
||||||
ns['ns']['vim_id'] = vim_res['vim_id']
|
ns['ns']['vim_id'] = vim_res['vim_id']
|
||||||
|
|
||||||
@ -810,75 +801,10 @@ class NfvoPlugin(nfvo_db_plugin.NfvoPluginDb, vnffg_db.VnffgPluginDbMixin,
|
|||||||
LOG.debug('vnffgd_templates: %s', vnffgd_templates)
|
LOG.debug('vnffgd_templates: %s', vnffgd_templates)
|
||||||
ns['vnffgd_templates'] = vnffgd_templates
|
ns['vnffgd_templates'] = vnffgd_templates
|
||||||
|
|
||||||
# Step-3
|
|
||||||
kwargs = {'ns': ns, 'params': param_values}
|
|
||||||
|
|
||||||
# NOTE NoTasksException is raised if no tasks.
|
|
||||||
workflow = self._vim_drivers.invoke(
|
|
||||||
driver_type,
|
|
||||||
'prepare_and_create_workflow',
|
|
||||||
resource='ns',
|
|
||||||
action='create',
|
|
||||||
auth_dict=self.get_auth_dict(context),
|
|
||||||
kwargs=kwargs)
|
|
||||||
try:
|
|
||||||
mistral_execution = self._vim_drivers.invoke(
|
|
||||||
driver_type,
|
|
||||||
'execute_workflow',
|
|
||||||
workflow=workflow,
|
|
||||||
auth_dict=self.get_auth_dict(context))
|
|
||||||
except Exception as ex:
|
|
||||||
LOG.error('Error while executing workflow: %s', ex)
|
|
||||||
self._vim_drivers.invoke(driver_type,
|
|
||||||
'delete_workflow',
|
|
||||||
workflow_id=workflow['id'],
|
|
||||||
auth_dict=self.get_auth_dict(context))
|
|
||||||
raise ex
|
|
||||||
ns_dict = super(NfvoPlugin, self).create_ns(context, ns)
|
ns_dict = super(NfvoPlugin, self).create_ns(context, ns)
|
||||||
|
|
||||||
def _create_ns_wait(self_obj, ns_id, execution_id):
|
|
||||||
exec_state = "RUNNING"
|
|
||||||
mistral_retries = MISTRAL_RETRIES
|
|
||||||
while exec_state == "RUNNING" and mistral_retries > 0:
|
|
||||||
time.sleep(MISTRAL_RETRY_WAIT)
|
|
||||||
exec_state = self._vim_drivers.invoke(
|
|
||||||
driver_type,
|
|
||||||
'get_execution',
|
|
||||||
execution_id=execution_id,
|
|
||||||
auth_dict=self.get_auth_dict(context)).state
|
|
||||||
LOG.debug('status: %s', exec_state)
|
|
||||||
if exec_state == 'SUCCESS' or exec_state == 'ERROR':
|
|
||||||
break
|
|
||||||
mistral_retries = mistral_retries - 1
|
|
||||||
# TODO(phuoc): add more information about error reason in case
|
|
||||||
# of exec_state is 'ERROR'
|
|
||||||
error_reason = None
|
|
||||||
if mistral_retries == 0 and exec_state == 'RUNNING':
|
|
||||||
error_reason = _(
|
|
||||||
"NS creation is not completed within"
|
|
||||||
" {wait} seconds as creation of mistral"
|
|
||||||
" execution {mistral} is not completed").format(
|
|
||||||
wait=MISTRAL_RETRIES * MISTRAL_RETRY_WAIT,
|
|
||||||
mistral=execution_id)
|
|
||||||
exec_obj = self._vim_drivers.invoke(
|
|
||||||
driver_type,
|
|
||||||
'get_execution',
|
|
||||||
execution_id=execution_id,
|
|
||||||
auth_dict=self.get_auth_dict(context))
|
|
||||||
self._vim_drivers.invoke(driver_type,
|
|
||||||
'delete_execution',
|
|
||||||
execution_id=execution_id,
|
|
||||||
auth_dict=self.get_auth_dict(context))
|
|
||||||
self._vim_drivers.invoke(driver_type,
|
|
||||||
'delete_workflow',
|
|
||||||
workflow_id=workflow['id'],
|
|
||||||
auth_dict=self.get_auth_dict(context))
|
|
||||||
super(NfvoPlugin, self).create_ns_post(
|
super(NfvoPlugin, self).create_ns_post(
|
||||||
context, ns_id, exec_obj, vnfd_dict,
|
context, ns_dict['id'], vnfd_dict, vnffgd_templates)
|
||||||
vnffgd_templates, error_reason)
|
|
||||||
|
|
||||||
self.spawn_n(_create_ns_wait, self, ns_dict['id'],
|
|
||||||
mistral_execution.id)
|
|
||||||
return ns_dict
|
return ns_dict
|
||||||
|
|
||||||
@log.log
|
@log.log
|
||||||
@ -907,6 +833,7 @@ class NfvoPlugin(nfvo_db_plugin.NfvoPluginDb, vnffg_db.VnffgPluginDbMixin,
|
|||||||
else:
|
else:
|
||||||
raise cs.ParamYAMLInputMissing()
|
raise cs.ParamYAMLInputMissing()
|
||||||
|
|
||||||
|
# TODO(hiromu): Remove delete NS API after the deprecation is accepted.
|
||||||
@log.log
|
@log.log
|
||||||
def delete_ns(self, context, ns_id, ns=None):
|
def delete_ns(self, context, ns_id, ns=None):
|
||||||
# Extract "force_delete" from request's body
|
# Extract "force_delete" from request's body
|
||||||
@ -918,83 +845,7 @@ class NfvoPlugin(nfvo_db_plugin.NfvoPluginDb, vnffg_db.VnffgPluginDbMixin,
|
|||||||
raise exceptions.AdminRequired(reason="Admin only operation")
|
raise exceptions.AdminRequired(reason="Admin only operation")
|
||||||
ns = super(NfvoPlugin, self).get_ns(context, ns_id)
|
ns = super(NfvoPlugin, self).get_ns(context, ns_id)
|
||||||
LOG.debug("Deleting ns: %s", ns)
|
LOG.debug("Deleting ns: %s", ns)
|
||||||
vim_res = self.vim_client.get_vim(context, ns['vim_id'])
|
|
||||||
super(NfvoPlugin, self).delete_ns_pre(context, ns_id, force_delete)
|
super(NfvoPlugin, self).delete_ns_pre(context, ns_id, force_delete)
|
||||||
driver_type = vim_res['vim_type']
|
|
||||||
workflow = None
|
|
||||||
try:
|
|
||||||
if ns['vnf_ids']:
|
|
||||||
ns['force_delete'] = force_delete
|
|
||||||
workflow = self._vim_drivers.invoke(
|
|
||||||
driver_type,
|
|
||||||
'prepare_and_create_workflow',
|
|
||||||
resource='ns',
|
|
||||||
action='delete',
|
|
||||||
auth_dict=self.get_auth_dict(context),
|
|
||||||
kwargs={'ns': ns})
|
|
||||||
except nfvo.NoTasksException:
|
|
||||||
LOG.warning("No VNF deletion task(s).")
|
|
||||||
if workflow:
|
|
||||||
try:
|
|
||||||
mistral_execution = self._vim_drivers.invoke(
|
|
||||||
driver_type,
|
|
||||||
'execute_workflow',
|
|
||||||
workflow=workflow,
|
|
||||||
auth_dict=self.get_auth_dict(context))
|
|
||||||
|
|
||||||
except Exception as ex:
|
|
||||||
LOG.error('Error while executing workflow: %s', ex)
|
|
||||||
self._vim_drivers.invoke(driver_type,
|
|
||||||
'delete_workflow',
|
|
||||||
workflow_id=workflow['id'],
|
|
||||||
auth_dict=self.get_auth_dict(context))
|
|
||||||
|
|
||||||
raise ex
|
|
||||||
|
|
||||||
def _delete_ns_wait(ns_id, execution_id):
|
|
||||||
exec_state = "RUNNING"
|
|
||||||
mistral_retries = MISTRAL_RETRIES
|
|
||||||
while exec_state == "RUNNING" and mistral_retries > 0:
|
|
||||||
time.sleep(MISTRAL_RETRY_WAIT)
|
|
||||||
exec_state = self._vim_drivers.invoke(
|
|
||||||
driver_type,
|
|
||||||
'get_execution',
|
|
||||||
execution_id=execution_id,
|
|
||||||
auth_dict=self.get_auth_dict(context)).state
|
|
||||||
LOG.debug('status: %s', exec_state)
|
|
||||||
if exec_state == 'SUCCESS' or exec_state == 'ERROR':
|
|
||||||
break
|
|
||||||
mistral_retries -= 1
|
|
||||||
# TODO(phuoc): add more information about error reason in case
|
|
||||||
# of exec_state is 'ERROR'
|
|
||||||
error_reason = None
|
|
||||||
if mistral_retries == 0 and exec_state == 'RUNNING':
|
|
||||||
error_reason = _(
|
|
||||||
"NS deletion is not completed within"
|
|
||||||
" {wait} seconds as deletion of mistral"
|
|
||||||
" execution {mistral} is not completed").format(
|
|
||||||
wait=MISTRAL_RETRIES * MISTRAL_RETRY_WAIT,
|
|
||||||
mistral=execution_id)
|
|
||||||
exec_obj = self._vim_drivers.invoke(
|
|
||||||
driver_type,
|
|
||||||
'get_execution',
|
|
||||||
execution_id=execution_id,
|
|
||||||
auth_dict=self.get_auth_dict(context))
|
|
||||||
self._vim_drivers.invoke(driver_type,
|
|
||||||
'delete_execution',
|
|
||||||
execution_id=execution_id,
|
|
||||||
auth_dict=self.get_auth_dict(context))
|
|
||||||
self._vim_drivers.invoke(driver_type,
|
|
||||||
'delete_workflow',
|
|
||||||
workflow_id=workflow['id'],
|
|
||||||
auth_dict=self.get_auth_dict(context))
|
|
||||||
super(NfvoPlugin, self).delete_ns_post(context, ns_id, exec_obj,
|
|
||||||
error_reason,
|
|
||||||
force_delete=force_delete)
|
|
||||||
|
|
||||||
if workflow:
|
|
||||||
self.spawn_n(_delete_ns_wait, ns['id'], mistral_execution.id)
|
|
||||||
else:
|
|
||||||
super(NfvoPlugin, self).delete_ns_post(
|
super(NfvoPlugin, self).delete_ns_post(
|
||||||
context, ns_id, None, None, force_delete=force_delete)
|
context, ns_id, force_delete=force_delete)
|
||||||
return ns['id']
|
return ns['id']
|
||||||
|
@ -1,403 +0,0 @@
|
|||||||
# All Rights Reserved.
|
|
||||||
#
|
|
||||||
# Licensed under the Apache License, Version 2.0 (the "License"); you may
|
|
||||||
# not use this file except in compliance with the License. You may obtain
|
|
||||||
# a copy of the License at
|
|
||||||
#
|
|
||||||
# http://www.apache.org/licenses/LICENSE-2.0
|
|
||||||
#
|
|
||||||
# Unless required by applicable law or agreed to in writing, software
|
|
||||||
# distributed under the License is distributed on an "AS IS" BASIS, WITHOUT
|
|
||||||
# WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the
|
|
||||||
# License for the specific language governing permissions and limitations
|
|
||||||
# under the License.
|
|
||||||
|
|
||||||
from tacker import context
|
|
||||||
from tacker.nfvo.drivers.workflow import workflow_generator
|
|
||||||
from tacker.tests.unit import base
|
|
||||||
|
|
||||||
|
|
||||||
def get_dummy_ns():
|
|
||||||
return {'ns': {'description': '',
|
|
||||||
'tenant_id': 'a81900a92bda40588c52699e1873a92f',
|
|
||||||
'vim_id': '96025dd5-ca16-49f3-9823-958eb04260c4',
|
|
||||||
'vnf_ids': '', 'attributes': {},
|
|
||||||
'nsd_id': 'b8587afb-6099-4f56-abce-572c62e3d61d',
|
|
||||||
'name': 'test_create_ns'},
|
|
||||||
'vnfd_details': {'vnf1': {'instances': ['VNF1'],
|
|
||||||
'id': 'dec09ed4-f355-4ec8-a00b-8548f6575a80'},
|
|
||||||
'vnf2': {'instances': ['VNF2'],
|
|
||||||
'id': '9f8f2af7-6407-4f79-a6fe-302c56172231'}},
|
|
||||||
'placement_attr': {}}
|
|
||||||
|
|
||||||
|
|
||||||
def get_dummy_vnffg_ns():
|
|
||||||
return {
|
|
||||||
'ns': {
|
|
||||||
'description': '',
|
|
||||||
'vim_id': '96025dd5-ca16-49f3-9823-958eb04260c4',
|
|
||||||
'vnf_ids': '', 'attributes': {},
|
|
||||||
'nsd_id': 'b8587afb-6099-4f56-abce-572c62e3d61d',
|
|
||||||
'name': 'test_create_ns'},
|
|
||||||
'vnfd_details': {
|
|
||||||
'vnf1': {'instances': ['VNF1'],
|
|
||||||
'id': 'dec09ed4-f355-4ec8-a00b-8548f6575a80'},
|
|
||||||
'vnf2': {'instances': ['VNF2'],
|
|
||||||
'id': '9f8f2af7-6407-4f79-a6fe-302c56172231'}},
|
|
||||||
'placement_attr': {},
|
|
||||||
'vnffgd_templates': {
|
|
||||||
'VNFFG1': {
|
|
||||||
'tosca_definitions_version':
|
|
||||||
'tosca_simple_profile_for_nfv_1_0_0',
|
|
||||||
'description': 'VNFFG1 descriptor',
|
|
||||||
'topology_template': {
|
|
||||||
'node_templates': {
|
|
||||||
'Forwarding_path1': {
|
|
||||||
'type': 'tosca.nodes.nfv.FP.TackerV2',
|
|
||||||
'description': 'creates path inside ns - test',
|
|
||||||
'properties': {
|
|
||||||
'policy': {
|
|
||||||
'type': 'ACL',
|
|
||||||
'criteria': [{
|
|
||||||
'classifier': {
|
|
||||||
'ip_proto': 6,
|
|
||||||
'network_src_port_id': {
|
|
||||||
'get_input': 'net_src_port_id'
|
|
||||||
},
|
|
||||||
'ip_dst_prefix': {
|
|
||||||
'get_input': 'ip_dest_prefix'
|
|
||||||
},
|
|
||||||
'destination_port_range': '80-1024'
|
|
||||||
},
|
|
||||||
'name': 'block_tcp'}]},
|
|
||||||
'path': [
|
|
||||||
{'capability': 'CP12',
|
|
||||||
'forwarder': 'vnf1'},
|
|
||||||
{'capability': 'CP22',
|
|
||||||
'forwarder': 'vnf2'}],
|
|
||||||
'id': 51}}},
|
|
||||||
'groups': {
|
|
||||||
'VNFFG1': {
|
|
||||||
'type': 'tosca.groups.nfv.VNFFG',
|
|
||||||
'description': 'HTTP to Corporate Net',
|
|
||||||
'members': ['Forwarding_path1'],
|
|
||||||
'properties': {
|
|
||||||
'version': 1.0,
|
|
||||||
'vendor': 'tacker',
|
|
||||||
'constituent_vnfs': ['vnf1', 'vnf2'],
|
|
||||||
'connection_point': ['CP12', 'CP22'],
|
|
||||||
'number_of_endpoints': 2,
|
|
||||||
'dependent_virtual_link': ['VL1', 'VL2']}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
def get_dummy_param():
|
|
||||||
return {'vnf1': {'substitution_mappings': {'VL1b8587afb-60': {
|
|
||||||
'type': 'tosca.nodes.nfv.VL', 'properties': {
|
|
||||||
'network_name': 'net_mgmt',
|
|
||||||
'vendor': 'tacker'}}, 'requirements': {
|
|
||||||
'virtualLink2': 'VL2b8587afb-60',
|
|
||||||
'virtualLink1': 'VL1b8587afb-60'}, 'VL2b8587afb-60': {
|
|
||||||
'type': 'tosca.nodes.nfv.VL',
|
|
||||||
'properties': {'network_name': 'net0',
|
|
||||||
'vendor': 'tacker'}}}},
|
|
||||||
'nsd': {'vl2_name': 'net0', 'vl1_name': 'net_mgmt'}}
|
|
||||||
|
|
||||||
|
|
||||||
def get_dummy_create_workflow():
|
|
||||||
return {'std.create_ns_dummy': {'input': ['ns'],
|
|
||||||
'tasks': {
|
|
||||||
'wait_vnf_active_VNF2': {
|
|
||||||
'action': 'tacker.show_vnf vnf=<% $.vnf_id_VNF2 %>',
|
|
||||||
'retry': {'count': 10, 'delay': 10,
|
|
||||||
'continue-on': '<% $.status_VNF2 = '
|
|
||||||
'"PENDING_CREATE" %>',
|
|
||||||
'break-on': '<% $.status_VNF2 = "ERROR" %>'},
|
|
||||||
'publish': {
|
|
||||||
'status_VNF2': '<% task(wait_vnf_active_VNF2).'
|
|
||||||
'result.vnf.status %>',
|
|
||||||
'mgmt_ip_address_VNF2': ' <% task('
|
|
||||||
'wait_vnf_active_VNF2).'
|
|
||||||
'result.vnf.'
|
|
||||||
'mgmt_ip_address %>'},
|
|
||||||
'on-success': [{
|
|
||||||
'delete_vnf_VNF2': '<% $.status_VNF2='
|
|
||||||
'"ERROR" %>'}]},
|
|
||||||
'create_ns_VNF2': {
|
|
||||||
'action': 'tacker.create_vnf body=<% $.ns.VNF2 %>',
|
|
||||||
'input': {'body': '<% $.ns.VNF2 %>'},
|
|
||||||
'publish': {
|
|
||||||
'status_VNF2': '<% task(create_ns_VNF2).'
|
|
||||||
'result.vnf.status %>',
|
|
||||||
'vim_id_VNF2': '<% task(create_ns_VNF2).'
|
|
||||||
'result.vnf.vim_id %>',
|
|
||||||
'mgmt_ip_address_VNF2': '<% task('
|
|
||||||
'create_ns_VNF2).'
|
|
||||||
'result.vnf.'
|
|
||||||
'mgmt_ip_address %>',
|
|
||||||
'vnf_id_VNF2': '<% task(create_ns_VNF2)'
|
|
||||||
'.result.vnf.id %>'},
|
|
||||||
'on-success': ['wait_vnf_active_VNF2']},
|
|
||||||
'create_ns_VNF1': {
|
|
||||||
'action': 'tacker.create_vnf body=<% $.ns.VNF1 %>',
|
|
||||||
'input': {'body': '<% $.ns.VNF1 %>'},
|
|
||||||
'publish': {
|
|
||||||
'status_VNF1': '<% task(create_ns_VNF1).'
|
|
||||||
'result.vnf.status %>',
|
|
||||||
'vnf_id_VNF1': '<% task(create_ns_VNF1).'
|
|
||||||
'result.vnf.id %>',
|
|
||||||
'mgmt_ip_address_VNF1': '<% task('
|
|
||||||
'create_ns_VNF1).'
|
|
||||||
'result.vnf.'
|
|
||||||
'mgmt_ip_address %>',
|
|
||||||
'vim_id_VNF1': '<% task(create_ns_VNF1).'
|
|
||||||
'result.vnf.vim_id %>'},
|
|
||||||
'on-success': ['wait_vnf_active_VNF1']},
|
|
||||||
'wait_vnf_active_VNF1': {
|
|
||||||
'action': 'tacker.show_vnf vnf=<% $.vnf_id_VNF1 %>',
|
|
||||||
'retry': {'count': 10, 'delay': 10,
|
|
||||||
'continue-on': '<% $.status_VNF1 = "PENDING_'
|
|
||||||
'CREATE" %>',
|
|
||||||
'break-on': '<% $.status_VNF1 = "ERROR" %>'},
|
|
||||||
'publish': {
|
|
||||||
'status_VNF1': '<% task(wait_vnf_active_VNF1).'
|
|
||||||
'result.vnf.status %>',
|
|
||||||
'mgmt_ip_address_VNF1': ' <% task('
|
|
||||||
'wait_vnf_active_VNF1).'
|
|
||||||
'result.vnf.'
|
|
||||||
'mgmt_ip_address %>'},
|
|
||||||
'on-success': [{'delete_vnf_VNF1': '<% $.status_VNF1='
|
|
||||||
'"ERROR" %>'}]},
|
|
||||||
'delete_vnf_VNF1': {
|
|
||||||
'action': 'tacker.delete_vnf vnf=<% $.vnf_id_VNF1%>',
|
|
||||||
'input': {'body': {'vnf': {'attributes': {
|
|
||||||
'force': False}}}}},
|
|
||||||
'delete_vnf_VNF2': {
|
|
||||||
'action': 'tacker.delete_vnf vnf=<% $.vnf_id_VNF2%>',
|
|
||||||
'input': {'body': {'vnf': {'attributes': {
|
|
||||||
'force': False}}}}}},
|
|
||||||
'type': 'direct', 'output': {
|
|
||||||
'status_VNF1': '<% $.status_VNF1 %>',
|
|
||||||
'status_VNF2': '<% $.status_VNF2 %>',
|
|
||||||
'mgmt_ip_address_VNF2': '<% $.mgmt_ip_address_VNF2 %>',
|
|
||||||
'mgmt_ip_address_VNF1': '<% $.mgmt_ip_address_VNF1 %>',
|
|
||||||
'vim_id_VNF2': '<% $.vim_id_VNF2 %>',
|
|
||||||
'vnf_id_VNF1': '<% $.vnf_id_VNF1 %>',
|
|
||||||
'vnf_id_VNF2': '<% $.vnf_id_VNF2 %>',
|
|
||||||
'vim_id_VNF1': '<% $.vim_id_VNF1 %>'}},
|
|
||||||
'version': '2.0'}
|
|
||||||
|
|
||||||
|
|
||||||
def get_dummy_create_vnffg_ns_workflow():
|
|
||||||
return {
|
|
||||||
'std.create_ns_dummy': {
|
|
||||||
'input': ['ns'],
|
|
||||||
'tasks': {
|
|
||||||
'wait_vnf_active_VNF2': {
|
|
||||||
'action': 'tacker.show_vnf vnf=<% $.vnf_id_VNF2 %>',
|
|
||||||
'retry': {
|
|
||||||
'count': 10,
|
|
||||||
'delay': 10,
|
|
||||||
'continue-on':
|
|
||||||
'<% $.status_VNF2 = "PENDING_CREATE" %>',
|
|
||||||
'break-on':
|
|
||||||
'<% $.status_VNF2 = "ERROR" %>'},
|
|
||||||
'publish': {
|
|
||||||
'status_VNF2':
|
|
||||||
'<% task(wait_vnf_active_VNF2).result.'
|
|
||||||
'vnf.status %>',
|
|
||||||
'mgmt_ip_address_VNF2':
|
|
||||||
' <% task(wait_vnf_active_VNF2).result.'
|
|
||||||
'vnf.mgmt_ip_address %>'},
|
|
||||||
'on-success': [
|
|
||||||
{'delete_vnf_VNF2': '<% $.status_VNF2="ERROR" %>'},
|
|
||||||
'create_vnffg_VNFFG1']},
|
|
||||||
'create_vnffg_VNFFG1': {
|
|
||||||
'action': 'tacker.create_vnffg body=<% $.ns.VNFFG1 %>',
|
|
||||||
'input': {'body': '<% $.ns.VNFFG1 %>'},
|
|
||||||
'join': 'all',
|
|
||||||
'publish': {
|
|
||||||
'vnffg_id_VNFFG1': '<% task(create_vnffg_VNFFG1).'
|
|
||||||
'result.vnffg.id %>'}},
|
|
||||||
'wait_vnf_active_VNF1': {
|
|
||||||
'action': 'tacker.show_vnf vnf=<% $.vnf_id_VNF1 %>',
|
|
||||||
'retry': {
|
|
||||||
'count': 10,
|
|
||||||
'delay': 10,
|
|
||||||
'continue-on':
|
|
||||||
'<% $.status_VNF1 = "PENDING_CREATE" %>',
|
|
||||||
'break-on':
|
|
||||||
'<% $.status_VNF1 = "ERROR" %>'},
|
|
||||||
'publish': {
|
|
||||||
'status_VNF1':
|
|
||||||
'<% task(wait_vnf_active_VNF1).result.'
|
|
||||||
'vnf.status %>',
|
|
||||||
'mgmt_ip_address_VNF1':
|
|
||||||
' <% task(wait_vnf_active_VNF1).result.'
|
|
||||||
'vnf.mgmt_ip_address %>'},
|
|
||||||
'on-success': [
|
|
||||||
{'delete_vnf_VNF1': '<% $.status_VNF1="ERROR" %>'},
|
|
||||||
'create_vnffg_VNFFG1']},
|
|
||||||
'create_ns_VNF1': {
|
|
||||||
'action': 'tacker.create_vnf body=<% $.ns.VNF1 %>',
|
|
||||||
'input': {'body': '<% $.ns.VNF1 %>'},
|
|
||||||
'publish': {
|
|
||||||
'status_VNF1':
|
|
||||||
'<% task(create_ns_VNF1).result.vnf.status %>',
|
|
||||||
'vnf_id_VNF1':
|
|
||||||
'<% task(create_ns_VNF1).result.vnf.id %>',
|
|
||||||
'mgmt_ip_address_VNF1':
|
|
||||||
'<% task(create_ns_VNF1).result.'
|
|
||||||
'vnf.mgmt_ip_address %>',
|
|
||||||
'vim_id_VNF1':
|
|
||||||
'<% task(create_ns_VNF1).result.vnf.vim_id %>'},
|
|
||||||
'on-success': ['wait_vnf_active_VNF1']},
|
|
||||||
'create_ns_VNF2': {
|
|
||||||
'action': 'tacker.create_vnf body=<% $.ns.VNF2 %>',
|
|
||||||
'input': {'body': '<% $.ns.VNF2 %>'},
|
|
||||||
'publish': {
|
|
||||||
'status_VNF2':
|
|
||||||
'<% task(create_ns_VNF2).result.vnf.status %>',
|
|
||||||
'vim_id_VNF2':
|
|
||||||
'<% task(create_ns_VNF2).result.vnf.vim_id %>',
|
|
||||||
'mgmt_ip_address_VNF2':
|
|
||||||
'<% task(create_ns_VNF2).result.'
|
|
||||||
'vnf.mgmt_ip_address %>',
|
|
||||||
'vnf_id_VNF2':
|
|
||||||
'<% task(create_ns_VNF2).result.vnf.id %>'},
|
|
||||||
'on-success': ['wait_vnf_active_VNF2']},
|
|
||||||
'delete_vnf_VNF1': {
|
|
||||||
'action': 'tacker.delete_vnf vnf=<% $.vnf_id_VNF1%>',
|
|
||||||
'input': {'body': {'vnf': {'attributes': {
|
|
||||||
'force': False}}}}},
|
|
||||||
'delete_vnf_VNF2': {
|
|
||||||
'action': 'tacker.delete_vnf vnf=<% $.vnf_id_VNF2%>',
|
|
||||||
'input': {'body': {'vnf': {'attributes': {
|
|
||||||
'force': False}}}}}},
|
|
||||||
'type': 'direct',
|
|
||||||
'output': {
|
|
||||||
'status_VNF1': '<% $.status_VNF1 %>',
|
|
||||||
'status_VNF2': '<% $.status_VNF2 %>',
|
|
||||||
'mgmt_ip_address_VNF2': '<% $.mgmt_ip_address_VNF2 %>',
|
|
||||||
'mgmt_ip_address_VNF1': '<% $.mgmt_ip_address_VNF1 %>',
|
|
||||||
'vnffg_id_VNFFG1': '<% $.vnffg_id_VNFFG1 %>',
|
|
||||||
'vim_id_VNF2': '<% $.vim_id_VNF2 %>',
|
|
||||||
'vnf_id_VNF1': '<% $.vnf_id_VNF1 %>',
|
|
||||||
'vnf_id_VNF2': '<% $.vnf_id_VNF2 %>',
|
|
||||||
'vim_id_VNF1': '<% $.vim_id_VNF1 %>'}},
|
|
||||||
'version': '2.0'}
|
|
||||||
|
|
||||||
|
|
||||||
def dummy_delete_ns_obj():
|
|
||||||
return {'vnf_ids': "{'VNF1': '5de5eca6-3e21-4bbd-a9d7-86458de75f0c'}",
|
|
||||||
'vnffg_ids': "{}"}
|
|
||||||
|
|
||||||
|
|
||||||
def dummy_delete_vnffg_ns_obj():
|
|
||||||
return {'vnf_ids': "{'VNF1': '5de5eca6-3e21-4bbd-a9d7-86458de75f0c'}",
|
|
||||||
'vnffg_ids': "{'VNFFG1': '99066f25-3124-44f1-bc5d-bc0bf236b012'}"}
|
|
||||||
|
|
||||||
|
|
||||||
def get_dummy_delete_workflow():
|
|
||||||
return {'version': '2.0',
|
|
||||||
'std.delete_ns_dummy': {
|
|
||||||
'input': ['vnf_id_VNF1'],
|
|
||||||
'tasks': {
|
|
||||||
'delete_vnf_VNF1': {
|
|
||||||
'action': 'tacker.delete_vnf vnf=<% $.vnf_id_VNF1%>',
|
|
||||||
'input': {'body': {'vnf': {'attributes': {
|
|
||||||
'force': False}}}}}},
|
|
||||||
'type': 'direct'}}
|
|
||||||
|
|
||||||
|
|
||||||
def get_dummy_delete_vnffg_ns_workflow():
|
|
||||||
return {'version': '2.0',
|
|
||||||
'std.delete_ns_dummy': {
|
|
||||||
'input': ['vnf_id_VNF1', 'VNFFG1'],
|
|
||||||
'tasks': {
|
|
||||||
'delete_vnf_VNF1': {
|
|
||||||
'join': 'all',
|
|
||||||
'action': 'tacker.delete_vnf vnf=<% $.vnf_id_VNF1%>',
|
|
||||||
'input': {'body': {'vnf': {'attributes': {
|
|
||||||
'force': False}}}}},
|
|
||||||
'delete_vnffg_VNFFG1': {
|
|
||||||
'action': 'tacker.delete_vnffg vnffg='
|
|
||||||
'<% $.VNFFG1 %>',
|
|
||||||
'on-success': ['delete_vnf_VNF1']}},
|
|
||||||
'type': 'direct'}}
|
|
||||||
|
|
||||||
|
|
||||||
class FakeMistral(object):
|
|
||||||
def __init__(self):
|
|
||||||
pass
|
|
||||||
|
|
||||||
|
|
||||||
class FakeNFVOPlugin(object):
|
|
||||||
|
|
||||||
def __init__(self, context, client, resource, action):
|
|
||||||
self.context = context
|
|
||||||
self.client = client
|
|
||||||
self.wg = workflow_generator.WorkflowGenerator(resource, action)
|
|
||||||
|
|
||||||
def prepare_workflow(self, **kwargs):
|
|
||||||
self.wg.task(**kwargs)
|
|
||||||
|
|
||||||
|
|
||||||
class TestWorkflowGenerator(base.TestCase):
|
|
||||||
def setUp(self):
|
|
||||||
super(TestWorkflowGenerator, self).setUp()
|
|
||||||
self.mistral_client = FakeMistral()
|
|
||||||
|
|
||||||
def test_prepare_workflow_create(self):
|
|
||||||
fPlugin = FakeNFVOPlugin(context, self.mistral_client,
|
|
||||||
resource='ns', action='create')
|
|
||||||
fPlugin.prepare_workflow(ns=get_dummy_ns(), params=get_dummy_param())
|
|
||||||
wf_def_values = [fPlugin.wg.definition[k] for
|
|
||||||
k in fPlugin.wg.definition]
|
|
||||||
self.assertIn(get_dummy_create_workflow()['std.create_ns_dummy'],
|
|
||||||
wf_def_values)
|
|
||||||
self.assertEqual(get_dummy_create_workflow()['version'],
|
|
||||||
fPlugin.wg.definition['version'])
|
|
||||||
|
|
||||||
def test_prepare_vnffg_ns_workflow_create(self):
|
|
||||||
fPlugin = FakeNFVOPlugin(context, self.mistral_client,
|
|
||||||
resource='ns', action='create')
|
|
||||||
fPlugin.prepare_workflow(ns=get_dummy_vnffg_ns(),
|
|
||||||
params=get_dummy_param())
|
|
||||||
wf_def_values = [fPlugin.wg.definition[k] for
|
|
||||||
k in fPlugin.wg.definition]
|
|
||||||
self.assertIn(
|
|
||||||
get_dummy_create_vnffg_ns_workflow()['std.create_ns_dummy'],
|
|
||||||
wf_def_values)
|
|
||||||
self.assertEqual(
|
|
||||||
get_dummy_create_vnffg_ns_workflow()['version'],
|
|
||||||
fPlugin.wg.definition['version'])
|
|
||||||
|
|
||||||
def test_prepare_workflow_delete(self):
|
|
||||||
fPlugin = FakeNFVOPlugin(context, self.mistral_client,
|
|
||||||
resource='ns', action='delete')
|
|
||||||
fPlugin.prepare_workflow(ns=dummy_delete_ns_obj())
|
|
||||||
wf_def_values = [fPlugin.wg.definition[k] for
|
|
||||||
k in fPlugin.wg.definition]
|
|
||||||
self.assertIn(get_dummy_delete_workflow()['std.delete_ns_dummy'],
|
|
||||||
wf_def_values)
|
|
||||||
self.assertEqual(get_dummy_delete_workflow()['version'],
|
|
||||||
fPlugin.wg.definition['version'])
|
|
||||||
|
|
||||||
def test_prepare_vnffg_ns_workflow_delete(self):
|
|
||||||
fPlugin = FakeNFVOPlugin(context, self.mistral_client,
|
|
||||||
resource='ns', action='delete')
|
|
||||||
fPlugin.prepare_workflow(ns=dummy_delete_vnffg_ns_obj())
|
|
||||||
wf_def_values = [fPlugin.wg.definition[k] for
|
|
||||||
k in fPlugin.wg.definition]
|
|
||||||
self.assertIn(
|
|
||||||
get_dummy_delete_vnffg_ns_workflow()['std.delete_ns_dummy'],
|
|
||||||
wf_def_values)
|
|
||||||
self.assertEqual(
|
|
||||||
get_dummy_delete_vnffg_ns_workflow()['version'],
|
|
||||||
fPlugin.wg.definition['version'])
|
|
@ -29,7 +29,6 @@ from tacker.db.nfvo import ns_db
|
|||||||
from tacker.db.nfvo import vnffg_db
|
from tacker.db.nfvo import vnffg_db
|
||||||
from tacker.extensions import nfvo
|
from tacker.extensions import nfvo
|
||||||
from tacker.manager import TackerManager
|
from tacker.manager import TackerManager
|
||||||
from tacker.nfvo.drivers.vim import openstack_driver
|
|
||||||
from tacker.nfvo import nfvo_plugin
|
from tacker.nfvo import nfvo_plugin
|
||||||
from tacker.plugins.common import constants
|
from tacker.plugins.common import constants
|
||||||
from tacker.tests import constants as test_constants
|
from tacker.tests import constants as test_constants
|
||||||
@ -62,22 +61,6 @@ class FakeDriverManager(mock.Mock):
|
|||||||
return uuidutils.generate_uuid()
|
return uuidutils.generate_uuid()
|
||||||
elif 'create_chain' in args:
|
elif 'create_chain' in args:
|
||||||
return uuidutils.generate_uuid(), uuidutils.generate_uuid()
|
return uuidutils.generate_uuid(), uuidutils.generate_uuid()
|
||||||
elif 'execute_workflow' in args:
|
|
||||||
mock_execution = mock.Mock()
|
|
||||||
mock_execution.id.return_value = \
|
|
||||||
"ba6bf017-f6f7-45f1-a280-57b073bf78ea"
|
|
||||||
return mock_execution
|
|
||||||
elif ('prepare_and_create_workflow' in args and
|
|
||||||
'delete' == kwargs['action'] and
|
|
||||||
DUMMY_NS_2 == kwargs['kwargs']['ns']['id']):
|
|
||||||
raise nfvo.NoTasksException(action=kwargs['action'],
|
|
||||||
resource=kwargs['kwargs']['ns']['id'])
|
|
||||||
elif ('prepare_and_create_workflow' in args and
|
|
||||||
'create' == kwargs['action'] and
|
|
||||||
utils.DUMMY_NS_2_NAME == kwargs['kwargs']['ns']['ns']['name']):
|
|
||||||
raise nfvo.NoTasksException(
|
|
||||||
action=kwargs['action'],
|
|
||||||
resource=kwargs['kwargs']['ns']['ns']['name'])
|
|
||||||
|
|
||||||
|
|
||||||
def get_by_name():
|
def get_by_name():
|
||||||
@ -1464,11 +1447,10 @@ class TestNfvoPlugin(db_base.SqlTestCase):
|
|||||||
@mock.patch.object(vim_client.VimClient, 'get_vim',
|
@mock.patch.object(vim_client.VimClient, 'get_vim',
|
||||||
return_value={"vim_type": "openstack"})
|
return_value={"vim_type": "openstack"})
|
||||||
@mock.patch.object(nfvo_plugin.NfvoPlugin, '_get_by_name')
|
@mock.patch.object(nfvo_plugin.NfvoPlugin, '_get_by_name')
|
||||||
@mock.patch.object(openstack_driver.OpenStack_Driver, 'get_mistral_client')
|
|
||||||
@mock.patch.object(uuidutils, 'generate_uuid',
|
@mock.patch.object(uuidutils, 'generate_uuid',
|
||||||
return_value=test_constants.UUID)
|
return_value=test_constants.UUID)
|
||||||
def test_create_ns(self, mock_uuid, mock_mistral_client,
|
def test_create_ns(self, mock_uuid, mock_get_by_name, mock_get_vimi,
|
||||||
mock_get_by_name, mock_get_vimi, mock_auth_dict):
|
mock_auth_dict):
|
||||||
self._insert_dummy_ns_template()
|
self._insert_dummy_ns_template()
|
||||||
self._insert_dummy_vim()
|
self._insert_dummy_vim()
|
||||||
mock_auth_dict.return_value = {
|
mock_auth_dict.return_value = {
|
||||||
@ -1478,62 +1460,6 @@ class TestNfvoPlugin(db_base.SqlTestCase):
|
|||||||
'project_name': 'dummy_project'
|
'project_name': 'dummy_project'
|
||||||
}
|
}
|
||||||
|
|
||||||
sample_yaml = 'std.create_ns' + test_constants.UUID + ':\n '\
|
|
||||||
'input:\n - ns\n output:\n mgmt_ip_address_VNF1: '\
|
|
||||||
'<% $.mgmt_ip_address_VNF1 %>\n mgmt_ip_address_VNF2: '\
|
|
||||||
'<% $.mgmt_ip_address_VNF2 %>\n status_VNF1: '\
|
|
||||||
'<% $.status_VNF1 %>\n status_VNF2: '\
|
|
||||||
'<% $.status_VNF2 %>\n vim_id_VNF1: <% $.vim_id_VNF1 %>\n'\
|
|
||||||
' vim_id_VNF2: <% $.vim_id_VNF2 %>\n vnf_id_VNF1: '\
|
|
||||||
'<% $.vnf_id_VNF1 %>\n vnf_id_VNF2: <% $.vnf_id_VNF2 %>\n '\
|
|
||||||
'tasks:\n create_ns_VNF1:\n action: tacker.create_vnf '\
|
|
||||||
'body=<% $.ns.VNF1 %>\n input:\n body: '\
|
|
||||||
'<% $.ns.VNF1 %>\n on-success:\n '\
|
|
||||||
'- wait_vnf_active_VNF1\n publish:\n '\
|
|
||||||
'mgmt_ip_address_VNF1: <% task(create_ns_VNF1).result.'\
|
|
||||||
'vnf.mgmt_ip_address %>\n status_VNF1: <% '\
|
|
||||||
'task(create_ns_VNF1).result.vnf.status %>\n'\
|
|
||||||
' vim_id_VNF1: <% task(create_ns_VNF1).'\
|
|
||||||
'result.vnf.vim_id %>\n vnf_id_VNF1: <% '\
|
|
||||||
'task(create_ns_VNF1).result.vnf.id %>\n'\
|
|
||||||
' create_ns_VNF2:\n action: tacker.create_vnf '\
|
|
||||||
'body=<% $.ns.VNF2 %>\n input:\n '\
|
|
||||||
'body: <% $.ns.VNF2 %>\n on-success:\n'\
|
|
||||||
' - wait_vnf_active_VNF2\n publish:\n '\
|
|
||||||
'mgmt_ip_address_VNF2: <% task(create_ns_VNF2).result.vnf.'\
|
|
||||||
'mgmt_ip_address %>\n status_VNF2: <% task(create_ns_VNF2)'\
|
|
||||||
'.result.vnf.status %>\n vim_id_VNF2: <% '\
|
|
||||||
'task(create_ns_VNF2).result.vnf.vim_id %>\n'\
|
|
||||||
' vnf_id_VNF2: <% task(create_ns_VNF2).result.vnf.id '\
|
|
||||||
'%>\n delete_vnf_VNF1:\n action: tacker.delete_vnf vnf'\
|
|
||||||
'=<% $.vnf_id_VNF1%>\n input:\n body:\n '\
|
|
||||||
'vnf:\n attributes:\n force: false\n'\
|
|
||||||
' delete_vnf_VNF2:\n action: tacker.delete_vnf'\
|
|
||||||
' vnf=<% $.vnf_id_VNF2%>\n input:\n body:\n'\
|
|
||||||
' vnf:\n attributes:\n '\
|
|
||||||
'force: false\n wait_vnf_active_VNF1:\n action:'\
|
|
||||||
' tacker.show_vnf vnf=<% $.vnf_id_VNF1 %>\n on-success:\n'\
|
|
||||||
' - delete_vnf_VNF1: <% $.status_VNF1="ERROR" %>\n '\
|
|
||||||
'publish:\n mgmt_ip_address_VNF1: \' <% '\
|
|
||||||
'task(wait_vnf_active_VNF1).result.vnf.mgmt_ip_address\n'\
|
|
||||||
' %>\'\n status_VNF1: <% '\
|
|
||||||
'task(wait_vnf_active_VNF1).result.vnf.status %>\n '\
|
|
||||||
'retry:\n break-on: <% $.status_VNF1 = "ERROR"'\
|
|
||||||
' %>\n continue-on: <% $.status_VNF1 = "PENDING_CREATE" '\
|
|
||||||
'%>\n count: 10\n delay: 10\n '\
|
|
||||||
'wait_vnf_active_VNF2:\n action: tacker.show_vnf vnf=<% '\
|
|
||||||
'$.vnf_id_VNF2 %>\n on-success:\n '\
|
|
||||||
'- delete_vnf_VNF2: <% $.status_VNF2="ERROR" %>\n '\
|
|
||||||
'publish:\n mgmt_ip_address_VNF2: \' <% '\
|
|
||||||
'task(wait_vnf_active_VNF2).result.vnf.mgmt_ip_address\n'\
|
|
||||||
' %>\'\n status_VNF2: '\
|
|
||||||
'<% task(wait_vnf_active_VNF2).result.vnf.status %>\n'\
|
|
||||||
' retry:\n break-on: <% $.status_VNF2 = '\
|
|
||||||
'"ERROR" %>\n continue-on: '\
|
|
||||||
'<% $.status_VNF2 = "PENDING_CREATE" %>\n '\
|
|
||||||
'count: 10\n '\
|
|
||||||
'delay: 10\n type: direct\nversion: \'2.0\'\n'
|
|
||||||
|
|
||||||
with patch.object(TackerManager, 'get_service_plugins') as \
|
with patch.object(TackerManager, 'get_service_plugins') as \
|
||||||
mock_plugins:
|
mock_plugins:
|
||||||
mock_plugins.return_value = {'VNFM': FakeVNFMPlugin()}
|
mock_plugins.return_value = {'VNFM': FakeVNFMPlugin()}
|
||||||
@ -1547,17 +1473,13 @@ class TestNfvoPlugin(db_base.SqlTestCase):
|
|||||||
self.assertEqual(ns_obj['ns']['name'], result['name'])
|
self.assertEqual(ns_obj['ns']['name'], result['name'])
|
||||||
self.assertIn('status', result)
|
self.assertIn('status', result)
|
||||||
self.assertIn('tenant_id', result)
|
self.assertIn('tenant_id', result)
|
||||||
mock_mistral_client().workflows.create.\
|
|
||||||
assert_called_with(sample_yaml)
|
|
||||||
|
|
||||||
@mock.patch.object(nfvo_plugin.NfvoPlugin, 'get_auth_dict')
|
@mock.patch.object(nfvo_plugin.NfvoPlugin, 'get_auth_dict')
|
||||||
@mock.patch.object(vim_client.VimClient, 'get_vim',
|
@mock.patch.object(vim_client.VimClient, 'get_vim',
|
||||||
return_value={"vim_type": "openstack"})
|
return_value={"vim_type": "openstack"})
|
||||||
@mock.patch.object(nfvo_plugin.NfvoPlugin, '_get_by_name')
|
@mock.patch.object(nfvo_plugin.NfvoPlugin, '_get_by_name')
|
||||||
@mock.patch.object(openstack_driver.OpenStack_Driver, 'get_mistral_client')
|
def test_create_ns_empty_description(self, mock_get_by_name, mock_get_vim,
|
||||||
def test_create_ns_empty_description(self, mock_mistral_client,
|
mock_auth_dict):
|
||||||
mock_get_by_name,
|
|
||||||
mock_get_vimi, mock_auth_dict):
|
|
||||||
self._insert_dummy_ns_template()
|
self._insert_dummy_ns_template()
|
||||||
self._insert_dummy_vim()
|
self._insert_dummy_vim()
|
||||||
mock_auth_dict.return_value = {
|
mock_auth_dict.return_value = {
|
||||||
@ -1583,8 +1505,7 @@ class TestNfvoPlugin(db_base.SqlTestCase):
|
|||||||
@mock.patch.object(vim_client.VimClient, 'get_vim',
|
@mock.patch.object(vim_client.VimClient, 'get_vim',
|
||||||
return_value={"vim_type": "openstack"})
|
return_value={"vim_type": "openstack"})
|
||||||
@mock.patch.object(nfvo_plugin.NfvoPlugin, '_get_by_name')
|
@mock.patch.object(nfvo_plugin.NfvoPlugin, '_get_by_name')
|
||||||
@mock.patch.object(openstack_driver.OpenStack_Driver, 'get_mistral_client')
|
def test_create_ns_inline(self, mock_get_by_name,
|
||||||
def test_create_ns_inline(self, mock_mistral_client, mock_get_by_name,
|
|
||||||
mock_get_vimi, mock_auth_dict, mock_create_nsd):
|
mock_get_vimi, mock_auth_dict, mock_create_nsd):
|
||||||
self._insert_dummy_ns_template_inline()
|
self._insert_dummy_ns_template_inline()
|
||||||
self._insert_dummy_vim()
|
self._insert_dummy_vim()
|
||||||
@ -1612,34 +1533,6 @@ class TestNfvoPlugin(db_base.SqlTestCase):
|
|||||||
self.assertIn('tenant_id', result)
|
self.assertIn('tenant_id', result)
|
||||||
mock_create_nsd.assert_called_once_with(mock.ANY, mock.ANY)
|
mock_create_nsd.assert_called_once_with(mock.ANY, mock.ANY)
|
||||||
|
|
||||||
@mock.patch.object(nfvo_plugin.NfvoPlugin, 'get_auth_dict')
|
|
||||||
@mock.patch.object(vim_client.VimClient, 'get_vim',
|
|
||||||
return_value={"vim_type": "openstack"})
|
|
||||||
@mock.patch.object(nfvo_plugin.NfvoPlugin, '_get_by_name')
|
|
||||||
@mock.patch('tacker.common.driver_manager.DriverManager.invoke',
|
|
||||||
side_effect=nfvo.NoTasksException(action='create',
|
|
||||||
resource='ns'))
|
|
||||||
def test_create_ns_workflow_no_task_exception(
|
|
||||||
self, mock_mistral_client, mock_get_by_name,
|
|
||||||
mock_get_vimi, mock_auth_dict):
|
|
||||||
self._insert_dummy_ns_template()
|
|
||||||
self._insert_dummy_vim()
|
|
||||||
mock_auth_dict.return_value = {
|
|
||||||
'auth_url': 'http://127.0.0.1',
|
|
||||||
'token': 'DummyToken',
|
|
||||||
'project_domain_name': 'dummy_domain',
|
|
||||||
'project_name': 'dummy_project'
|
|
||||||
}
|
|
||||||
with patch.object(TackerManager, 'get_service_plugins') as \
|
|
||||||
mock_plugins:
|
|
||||||
mock_plugins.return_value = {'VNFM': FakeVNFMPlugin()}
|
|
||||||
mock_get_by_name.return_value = get_by_name()
|
|
||||||
|
|
||||||
ns_obj = utils.get_dummy_ns_obj_2()
|
|
||||||
self.assertRaises(nfvo.NoTasksException,
|
|
||||||
self.nfvo_plugin.create_ns,
|
|
||||||
self.context, ns_obj)
|
|
||||||
|
|
||||||
@mock.patch.object(nfvo_plugin.NfvoPlugin, 'get_auth_dict')
|
@mock.patch.object(nfvo_plugin.NfvoPlugin, 'get_auth_dict')
|
||||||
@mock.patch.object(vim_client.VimClient, 'get_vim')
|
@mock.patch.object(vim_client.VimClient, 'get_vim')
|
||||||
@mock.patch.object(nfvo_plugin.NfvoPlugin, '_get_by_name')
|
@mock.patch.object(nfvo_plugin.NfvoPlugin, '_get_by_name')
|
||||||
@ -1662,33 +1555,6 @@ class TestNfvoPlugin(db_base.SqlTestCase):
|
|||||||
'ba6bf017-f6f7-45f1-a280-57b073bf78ea')
|
'ba6bf017-f6f7-45f1-a280-57b073bf78ea')
|
||||||
self.assertIsNotNone(result)
|
self.assertIsNotNone(result)
|
||||||
|
|
||||||
@mock.patch.object(nfvo_plugin.NfvoPlugin, 'get_auth_dict')
|
|
||||||
@mock.patch.object(vim_client.VimClient, 'get_vim')
|
|
||||||
@mock.patch.object(nfvo_plugin.NfvoPlugin, '_get_by_name')
|
|
||||||
@mock.patch("tacker.db.nfvo.ns_db.NSPluginDb.delete_ns_post")
|
|
||||||
def test_delete_ns_no_task_exception(
|
|
||||||
self, mock_delete_ns_post, mock_get_by_name, mock_get_vim,
|
|
||||||
mock_auth_dict):
|
|
||||||
|
|
||||||
self._insert_dummy_vim()
|
|
||||||
self._insert_dummy_ns_template()
|
|
||||||
self._insert_dummy_ns_2()
|
|
||||||
mock_auth_dict.return_value = {
|
|
||||||
'auth_url': 'http://127.0.0.1',
|
|
||||||
'token': 'DummyToken',
|
|
||||||
'project_domain_name': 'dummy_domain',
|
|
||||||
'project_name': 'dummy_project'
|
|
||||||
}
|
|
||||||
|
|
||||||
with patch.object(TackerManager, 'get_service_plugins') as \
|
|
||||||
mock_plugins:
|
|
||||||
mock_plugins.return_value = {'VNFM': FakeVNFMPlugin()}
|
|
||||||
mock_get_by_name.return_value = get_by_name()
|
|
||||||
self.nfvo_plugin.delete_ns(self.context,
|
|
||||||
DUMMY_NS_2)
|
|
||||||
mock_delete_ns_post.assert_called_with(
|
|
||||||
self.context, DUMMY_NS_2, None, None, force_delete=False)
|
|
||||||
|
|
||||||
@mock.patch.object(nfvo_plugin.NfvoPlugin, 'get_auth_dict')
|
@mock.patch.object(nfvo_plugin.NfvoPlugin, 'get_auth_dict')
|
||||||
@mock.patch.object(vim_client.VimClient, 'get_vim')
|
@mock.patch.object(vim_client.VimClient, 'get_vim')
|
||||||
@mock.patch.object(nfvo_plugin.NfvoPlugin, '_get_by_name')
|
@mock.patch.object(nfvo_plugin.NfvoPlugin, '_get_by_name')
|
||||||
|
Loading…
Reference in New Issue
Block a user