Merge lp:~emagana/neutron/plugin-framework-nx-os into lp:~cisco-openstack/neutron/plugin-framework
- plugin-framework-nx-os
- Merge into plugin-framework
Proposed by
Edgar Magana
Status: | Merged |
---|---|
Merged at revision: | 42 |
Proposed branch: | lp:~emagana/neutron/plugin-framework-nx-os |
Merge into: | lp:~cisco-openstack/neutron/plugin-framework |
Diff against target: |
479 lines (+315/-18) 5 files modified
quantum/plugins/cisco/README (+29/-7) quantum/plugins/cisco/common/cisco_configuration.py (+10/-0) quantum/plugins/cisco/l2network_plugin.py (+19/-3) quantum/plugins/cisco/nexus/cisco_nexus_network_driver.py (+236/-0) quantum/plugins/cisco/nexus/cisco_nexus_plugin.py (+21/-8) |
To merge this branch: | bzr merge lp:~emagana/neutron/plugin-framework-nx-os |
Related bugs: |
Reviewer | Review Type | Date Requested | Status |
---|---|---|---|
Sumit Naiksatam (community) | Approve | ||
Ram Durairaj | Pending | ||
Review via email: mp+70106@code.launchpad.net |
Commit message
Description of the change
Nexus OS driver integration
VLAN configuration to Nexus 7K Switch
To post a comment you must log in.
Preview Diff
[H/L] Next/Prev Comment, [J/K] Next/Prev File, [N/P] Next/Prev Hunk
1 | === modified file 'quantum/plugins/cisco/README' | |||
2 | --- quantum/plugins/cisco/README 2011-08-01 03:31:42 +0000 | |||
3 | +++ quantum/plugins/cisco/README 2011-08-02 04:45:54 +0000 | |||
4 | @@ -7,6 +7,7 @@ | |||
5 | 7 | * UCS B200 series blades with M81KR VIC installed. | 7 | * UCS B200 series blades with M81KR VIC installed. |
6 | 8 | * UCSM 2.0 (Capitola) Build 230 | 8 | * UCSM 2.0 (Capitola) Build 230 |
7 | 9 | * RHEL 6.1 | 9 | * RHEL 6.1 |
8 | 10 | * ncclcient v0.3.1 - Python library for NETCONF clients (http://schmizz.net/ncclient/) | ||
9 | 10 | * UCS & VIC installation (support for KVM) - please consult the accompanying installation guide available at: | 11 | * UCS & VIC installation (support for KVM) - please consult the accompanying installation guide available at: |
10 | 11 | http://wikicentral.cisco.com/display/GROUP/SAVBU+Palo+VM-FEX+for+Linux+KVM | 12 | http://wikicentral.cisco.com/display/GROUP/SAVBU+Palo+VM-FEX+for+Linux+KVM |
11 | 12 | * To run Quantum on RHEL, you will need to have the correct version of python-routes (version 1.12.3 or later). The RHEL 6.1 package contains an older version. Do the following and check your python-routes version: | 13 | * To run Quantum on RHEL, you will need to have the correct version of python-routes (version 1.12.3 or later). The RHEL 6.1 package contains an older version. Do the following and check your python-routes version: |
12 | @@ -37,7 +38,7 @@ | |||
13 | 37 | common/cisco_utils.py | 38 | common/cisco_utils.py |
14 | 38 | __init__.py | 39 | __init__.py |
15 | 39 | ucs/get-vif.sh | 40 | ucs/get-vif.sh |
17 | 40 | * Configure the L2 Network Pllugin: | 41 | * Configure the L2 Network Plugin: |
18 | 41 | + In cisco_configuration.py, | 42 | + In cisco_configuration.py, |
19 | 42 | - change the UCSM IP in the following statement to your UCSM IP | 43 | - change the UCSM IP in the following statement to your UCSM IP |
20 | 43 | flags.DEFINE_string('ucsm_ip_address', "172.20.231.27", 'IP address of UCSM') | 44 | flags.DEFINE_string('ucsm_ip_address', "172.20.231.27", 'IP address of UCSM') |
21 | @@ -57,12 +58,33 @@ | |||
22 | 57 | flags.DEFINE_string('profile_name_prefix', "q-", 'Prefix of the name given to the port profile') | 58 | flags.DEFINE_string('profile_name_prefix', "q-", 'Prefix of the name given to the port profile') |
23 | 58 | - Change the path to reflect the location of the get-vif.sh script, if you have followed the instructions in this README, this location should be the same as that of your other plugin modules | 59 | - Change the path to reflect the location of the get-vif.sh script, if you have followed the instructions in this README, this location should be the same as that of your other plugin modules |
24 | 59 | flags.DEFINE_string('get_next_vif', "/root/sumit/quantum/quantum/plugins/cisco/get-vif.sh", 'This is the location of the script to get the next available dynamic nic') | 60 | flags.DEFINE_string('get_next_vif', "/root/sumit/quantum/quantum/plugins/cisco/get-vif.sh", 'This is the location of the script to get the next available dynamic nic') |
31 | 60 | + In cisco_credentials.py, | 61 | |
32 | 61 | - Change the following stucture to reflect the correct UCS and Nova DB details. Your UCSM_IP_ADDRESS has to match the ucsmm_ip_addresss which you provided in the cisco_configuration file earlier. Similarly, your NOVA_DATABSE_IP has to match the db_server_ip which you provided earlier. DB_USERNAME and DB_PASSWORD are those which you provided for the Nova MySQL DB when you setup OpenStack | 62 | + In cisco_credentials.py, |
33 | 62 | _creds_dictionary = { | 63 | - Change the following structure to reflect the correct UCS, N7K and Nova DB details. Your UCSM_IP_ADDRESS has to match the ucsmm_ip_addresss which you provided in the cisco_configuration file earlier. Similarly, your NOVA_DATABSE_IP has to match the db_server_ip which you provided earlier. DB_USERNAME and DB_PASSWORD are those which you provided for the Nova MySQL DB when you setup OpenStack |
34 | 63 | 'UCSM_IP_ADDRESS':["UCSM_USERNAME", "UCSM_PASSWORD"], | 64 | N7K_IP_ADDRESS has to match with your Nexus 7k switch IP Address, N7K_USERNAME is the administrator user-name and N7K_PASSWORD is the password. |
35 | 64 | 'NOVA_DATABASE_IP':["DB_USERNAME", "DB_PASSWORD"] | 65 | _creds_dictionary = { |
36 | 65 | } | 66 | 'UCSM_IP_ADDRESS':["UCSM_USERNAME", "UCSM_PASSWORD"], |
37 | 67 | 'NOVA_DATABASE_IP':["DB_USERNAME", "DB_PASSWORD"] | ||
38 | 68 | } | ||
39 | 69 | |||
40 | 70 | * Configure the L2 Network Plugin with Nexus OS Driver for testing VLANs CRUD on Nexus 7k Switch. Making these changes requires one Nexus 7K Switch connected to the UCSM and the ncclient patch not just the regular library, otherwise the system will fail. | ||
41 | 71 | + In cisco_configuration.py, | ||
42 | 72 | - change the NEXUS 7K IP in the following statement to your N7K Switch IP | ||
43 | 73 | flags.DEFINE_string('nexus_ip_address', "172.20.231.61", 'IP address of N7K') | ||
44 | 74 | - change the NEXUS Interface in the following statement to the interface number in your N7K which is connected to your UCSM UpLink port | ||
45 | 75 | flags.DEFINE_string('nexus_port', "3/23", 'Port number of the Interface connected from the Nexus 7K Switch to UCSM 6120') | ||
46 | 76 | - change NEXUS Driver Flag to "on" in the following statement | ||
47 | 77 | flags.DEFINE_string('nexus_driver_active', "off", 'Flag to activate Nexus OS Driver') | ||
48 | 78 | |||
49 | 79 | + In cisco_credentials.py, | ||
50 | 80 | - Change the following structure to reflect the correct UCS, N7K and Nova DB details. Your UCSM_IP_ADDRESS has to match the ucsmm_ip_addresss which you provided in the cisco_configuration file earlier. Similarly, your NOVA_DATABSE_IP has to match the db_server_ip which you provided earlier. DB_USERNAME and DB_PASSWORD are those which you provided for the Nova MySQL DB when you setup OpenStack | ||
51 | 81 | N7K_IP_ADDRESS has to match with your Nexus 7k switch IP Address, N7K_USERNAME is the administrator user-name and N7K_PASSWORD is the password. | ||
52 | 82 | _creds_dictionary = { | ||
53 | 83 | 'UCSM_IP_ADDRESS':["UCSM_USERNAME", "UCSM_PASSWORD"], | ||
54 | 84 | 'N7K_IP_ADDRESS':["N7K_USERNAME", "N7K_PASSWORD"], | ||
55 | 85 | 'NOVA_DATABASE_IP':["DB_USERNAME", "DB_PASSWORD"] | ||
56 | 86 | } | ||
57 | 87 | |||
58 | 66 | * Start the Quantum service | 88 | * Start the Quantum service |
59 | 67 | 89 | ||
60 | 68 | ** Additional installation required on Nova Compute: | 90 | ** Additional installation required on Nova Compute: |
61 | 69 | 91 | ||
62 | === modified file 'quantum/plugins/cisco/common/cisco_configuration.py' | |||
63 | --- quantum/plugins/cisco/common/cisco_configuration.py 2011-07-31 18:38:26 +0000 | |||
64 | +++ quantum/plugins/cisco/common/cisco_configuration.py 2011-08-02 04:45:54 +0000 | |||
65 | @@ -15,6 +15,7 @@ | |||
66 | 15 | # under the License. | 15 | # under the License. |
67 | 16 | # | 16 | # |
68 | 17 | # @author: Sumit Naiksatam, Cisco Systems, Inc. | 17 | # @author: Sumit Naiksatam, Cisco Systems, Inc. |
69 | 18 | # @author: Edgar Magana, Cisco Systems, Inc. | ||
70 | 18 | # | 19 | # |
71 | 19 | from quantum.common import flags | 20 | from quantum.common import flags |
72 | 20 | 21 | ||
73 | @@ -26,6 +27,12 @@ | |||
74 | 26 | # | 27 | # |
75 | 27 | flags.DEFINE_string('ucsm_ip_address', "172.20.231.27", 'IP address of \ | 28 | flags.DEFINE_string('ucsm_ip_address', "172.20.231.27", 'IP address of \ |
76 | 28 | UCSM') | 29 | UCSM') |
77 | 30 | flags.DEFINE_string('nexus_ip_address', "172.20.231.61", 'IP address of \ | ||
78 | 31 | Nexus Switch') | ||
79 | 32 | flags.DEFINE_string('nexus_port', "3/23", 'Port number of the Interface \ | ||
80 | 33 | connected from the Nexus Switch to UCSM 6120') | ||
81 | 34 | flags.DEFINE_string('nexus_driver_active', "off", 'Flag to activate Nexus OS\ | ||
82 | 35 | Driver') | ||
83 | 29 | flags.DEFINE_string('db_server_ip', "127.0.0.1", 'IP address of nova DB \ | 36 | flags.DEFINE_string('db_server_ip', "127.0.0.1", 'IP address of nova DB \ |
84 | 30 | server') | 37 | server') |
85 | 31 | flags.DEFINE_string('nova_host_name', "openstack-0203", 'nova cloud \ | 38 | flags.DEFINE_string('nova_host_name', "openstack-0203", 'nova cloud \ |
86 | @@ -68,6 +75,9 @@ | |||
87 | 68 | 75 | ||
88 | 69 | # Inventory items | 76 | # Inventory items |
89 | 70 | UCSM_IP_ADDRESS = FLAGS.ucsm_ip_address | 77 | UCSM_IP_ADDRESS = FLAGS.ucsm_ip_address |
90 | 78 | NEXUS_IP_ADDRESS = FLAGS.nexus_ip_address | ||
91 | 79 | NEXUS_DRIVER_ACTIVE = FLAGS.nexus_driver_active | ||
92 | 80 | NEXUS_PORT = FLAGS.nexus_port | ||
93 | 71 | DB_SERVER_IP = FLAGS.db_server_ip | 81 | DB_SERVER_IP = FLAGS.db_server_ip |
94 | 72 | NOVA_HOST_NAME = FLAGS.nova_host_name | 82 | NOVA_HOST_NAME = FLAGS.nova_host_name |
95 | 73 | 83 | ||
96 | 74 | 84 | ||
97 | === modified file 'quantum/plugins/cisco/l2network_plugin.py' | |||
98 | --- quantum/plugins/cisco/l2network_plugin.py 2011-07-31 18:38:26 +0000 | |||
99 | +++ quantum/plugins/cisco/l2network_plugin.py 2011-08-02 04:45:54 +0000 | |||
100 | @@ -15,6 +15,7 @@ | |||
101 | 15 | # under the License. | 15 | # under the License. |
102 | 16 | # | 16 | # |
103 | 17 | # @author: Sumit Naiksatam, Cisco Systems, Inc. | 17 | # @author: Sumit Naiksatam, Cisco Systems, Inc. |
104 | 18 | # @author: Edgar Magana, Cisco Systems, Inc. | ||
105 | 18 | # | 19 | # |
106 | 19 | 20 | ||
107 | 20 | import logging as LOG | 21 | import logging as LOG |
108 | @@ -65,8 +66,13 @@ | |||
109 | 65 | new_net_id = self._get_unique_net_id(tenant_id) | 66 | new_net_id = self._get_unique_net_id(tenant_id) |
110 | 66 | vlan_id = self._get_vlan_for_tenant(tenant_id, net_name) | 67 | vlan_id = self._get_vlan_for_tenant(tenant_id, net_name) |
111 | 67 | vlan_name = self._get_vlan_name(new_net_id, str(vlan_id)) | 68 | vlan_name = self._get_vlan_name(new_net_id, str(vlan_id)) |
113 | 68 | self._nexus_plugin.create_network(tenant_id, net_name, new_net_id, | 69 | nexus_driver_flag = conf.NEXUS_DRIVER_ACTIVE |
114 | 70 | if nexus_driver_flag == 'on': | ||
115 | 71 | LOG.debug("Nexus OS Driver called\n") | ||
116 | 72 | self._nexus_plugin.create_network(tenant_id, net_name, new_net_id, | ||
117 | 69 | vlan_name, vlan_id) | 73 | vlan_name, vlan_id) |
118 | 74 | else: | ||
119 | 75 | LOG.debug("No Nexus OS Driver available\n") | ||
120 | 70 | self._ucs_plugin.create_network(tenant_id, net_name, new_net_id, | 76 | self._ucs_plugin.create_network(tenant_id, net_name, new_net_id, |
121 | 71 | vlan_name, vlan_id) | 77 | vlan_name, vlan_id) |
122 | 72 | new_net_dict = {const.NET_ID: new_net_id, | 78 | new_net_dict = {const.NET_ID: new_net_id, |
123 | @@ -88,12 +94,17 @@ | |||
124 | 88 | """ | 94 | """ |
125 | 89 | LOG.debug("delete_network() called\n") | 95 | LOG.debug("delete_network() called\n") |
126 | 90 | net = self._networks.get(net_id) | 96 | net = self._networks.get(net_id) |
127 | 97 | nexus_driver_flag = conf.NEXUS_DRIVER_ACTIVE | ||
128 | 91 | # TODO (Sumit) : Verify that no attachments are plugged into the | 98 | # TODO (Sumit) : Verify that no attachments are plugged into the |
129 | 92 | # network | 99 | # network |
130 | 93 | if net: | 100 | if net: |
131 | 94 | # TODO (Sumit) : Before deleting the network, make sure all the | 101 | # TODO (Sumit) : Before deleting the network, make sure all the |
132 | 95 | # ports associated with this network are also deleted | 102 | # ports associated with this network are also deleted |
134 | 96 | self._nexus_plugin.delete_network(tenant_id, net_id) | 103 | if nexus_driver_flag == 'on': |
135 | 104 | LOG.debug("Nexus OS Driver called\n") | ||
136 | 105 | self._nexus_plugin.delete_network(tenant_id, net_id) | ||
137 | 106 | else: | ||
138 | 107 | LOG.debug("No Nexus OS Driver available\n") | ||
139 | 97 | self._ucs_plugin.delete_network(tenant_id, net_id) | 108 | self._ucs_plugin.delete_network(tenant_id, net_id) |
140 | 98 | self._networks.pop(net_id) | 109 | self._networks.pop(net_id) |
141 | 99 | tenant = self._get_tenant(tenant_id) | 110 | tenant = self._get_tenant(tenant_id) |
142 | @@ -118,7 +129,12 @@ | |||
143 | 118 | Virtual Network. | 129 | Virtual Network. |
144 | 119 | """ | 130 | """ |
145 | 120 | LOG.debug("rename_network() called\n") | 131 | LOG.debug("rename_network() called\n") |
147 | 121 | self._nexus_plugin.rename_network(tenant_id, net_id) | 132 | nexus_driver_flag = conf.NEXUS_DRIVER_ACTIVE |
148 | 133 | if nexus_driver_flag == 'on': | ||
149 | 134 | LOG.debug("Nexus OS Driver called\n") | ||
150 | 135 | self._nexus_plugin.rename_network(tenant_id, net_id) | ||
151 | 136 | else: | ||
152 | 137 | LOG.debug("No Nexus OS Driver available\n") | ||
153 | 122 | self._ucs_plugin.rename_network(tenant_id, net_id) | 138 | self._ucs_plugin.rename_network(tenant_id, net_id) |
154 | 123 | network = self._get_network(tenant_id, net_id) | 139 | network = self._get_network(tenant_id, net_id) |
155 | 124 | network[const.NET_NAME] = new_name | 140 | network[const.NET_NAME] = new_name |
156 | 125 | 141 | ||
157 | === added file 'quantum/plugins/cisco/nexus/cisco_nexus_network_driver.py' | |||
158 | --- quantum/plugins/cisco/nexus/cisco_nexus_network_driver.py 1970-01-01 00:00:00 +0000 | |||
159 | +++ quantum/plugins/cisco/nexus/cisco_nexus_network_driver.py 2011-08-02 04:45:54 +0000 | |||
160 | @@ -0,0 +1,236 @@ | |||
161 | 1 | # vim: tabstop=4 shiftwidth=4 softtabstop=4 | ||
162 | 2 | # | ||
163 | 3 | # Copyright 2011 Cisco Systems, Inc. All rights reserved. | ||
164 | 4 | # | ||
165 | 5 | # Licensed under the Apache License, Version 2.0 (the "License"); you may | ||
166 | 6 | # not use this file except in compliance with the License. You may obtain | ||
167 | 7 | # a copy of the License at | ||
168 | 8 | # | ||
169 | 9 | # http://www.apache.org/licenses/LICENSE-2.0 | ||
170 | 10 | # | ||
171 | 11 | # Unless required by applicable law or agreed to in writing, software | ||
172 | 12 | # distributed under the License is distributed on an "AS IS" BASIS, WITHOUT | ||
173 | 13 | # WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the | ||
174 | 14 | # License for the specific language governing permissions and limitations | ||
175 | 15 | # under the License. | ||
176 | 16 | # | ||
177 | 17 | # @author: Debojyoti Dutta, Cisco Systems, Inc. | ||
178 | 18 | # @author: Edgar Magana, Cisco Systems Inc. | ||
179 | 19 | # | ||
180 | 20 | """ | ||
181 | 21 | Implements a Nexus-OS NETCONF over SSHv2 API Client | ||
182 | 22 | """ | ||
183 | 23 | |||
184 | 24 | import logging as LOG | ||
185 | 25 | import string | ||
186 | 26 | import subprocess | ||
187 | 27 | |||
188 | 28 | from quantum.plugins.cisco.common import cisco_configuration as conf | ||
189 | 29 | from quantum.plugins.cisco.common import cisco_constants as const | ||
190 | 30 | from quantum.plugins.cisco.common import cisco_exceptions as cexc | ||
191 | 31 | |||
192 | 32 | from ncclient import manager | ||
193 | 33 | |||
194 | 34 | LOG.basicConfig(level=LOG.WARN) | ||
195 | 35 | LOG.getLogger(const.LOGGER_COMPONENT_NAME) | ||
196 | 36 | |||
197 | 37 | |||
198 | 38 | # The following are standard strings, messages used to communicate with Nexus, | ||
199 | 39 | #only place holder values change for each message | ||
200 | 40 | exec_conf_prefix = """ | ||
201 | 41 | <config xmlns:xc="urn:ietf:params:xml:ns:netconf:base:1.0"> | ||
202 | 42 | <configure xmlns="http://www.cisco.com/nxos:1.0:vlan_mgr_cli"> | ||
203 | 43 | <__XML__MODE__exec_configure> | ||
204 | 44 | """ | ||
205 | 45 | |||
206 | 46 | |||
207 | 47 | exec_conf_postfix = """ | ||
208 | 48 | </__XML__MODE__exec_configure> | ||
209 | 49 | </configure> | ||
210 | 50 | </config> | ||
211 | 51 | """ | ||
212 | 52 | |||
213 | 53 | |||
214 | 54 | cmd_vlan_conf_snippet = """ | ||
215 | 55 | <vlan> | ||
216 | 56 | <vlan-id-create-delete> | ||
217 | 57 | <__XML__PARAM_value>%s</__XML__PARAM_value> | ||
218 | 58 | <__XML__MODE_vlan> | ||
219 | 59 | <name> | ||
220 | 60 | <vlan-name>%s</vlan-name> | ||
221 | 61 | </name> | ||
222 | 62 | <state> | ||
223 | 63 | <vstate>active</vstate> | ||
224 | 64 | </state> | ||
225 | 65 | <no> | ||
226 | 66 | <shutdown/> | ||
227 | 67 | </no> | ||
228 | 68 | </__XML__MODE_vlan> | ||
229 | 69 | </vlan-id-create-delete> | ||
230 | 70 | </vlan> | ||
231 | 71 | """ | ||
232 | 72 | |||
233 | 73 | cmd_no_vlan_conf_snippet = """ | ||
234 | 74 | <no> | ||
235 | 75 | <vlan> | ||
236 | 76 | <vlan-id-create-delete> | ||
237 | 77 | <__XML__PARAM_value>%s</__XML__PARAM_value> | ||
238 | 78 | </vlan-id-create-delete> | ||
239 | 79 | </vlan> | ||
240 | 80 | </no> | ||
241 | 81 | """ | ||
242 | 82 | |||
243 | 83 | cmd_vlan_int_snippet = """ | ||
244 | 84 | <interface> | ||
245 | 85 | <ethernet> | ||
246 | 86 | <interface>%s</interface> | ||
247 | 87 | <__XML__MODE_if-ethernet-switch> | ||
248 | 88 | <switchport></switchport> | ||
249 | 89 | <switchport> | ||
250 | 90 | <trunk> | ||
251 | 91 | <allowed> | ||
252 | 92 | <vlan> | ||
253 | 93 | <__XML__BLK_Cmd_switchport_trunk_allowed_allow-vlans> | ||
254 | 94 | <allow-vlans>%s</allow-vlans> | ||
255 | 95 | </__XML__BLK_Cmd_switchport_trunk_allowed_allow-vlans> | ||
256 | 96 | </vlan> | ||
257 | 97 | </allowed> | ||
258 | 98 | </trunk> | ||
259 | 99 | </switchport> | ||
260 | 100 | </__XML__MODE_if-ethernet-switch> | ||
261 | 101 | </ethernet> | ||
262 | 102 | </interface> | ||
263 | 103 | """ | ||
264 | 104 | |||
265 | 105 | cmd_port_trunk = """ | ||
266 | 106 | <interface> | ||
267 | 107 | <ethernet> | ||
268 | 108 | <interface>%s</interface> | ||
269 | 109 | <__XML__MODE_if-ethernet-switch> | ||
270 | 110 | <switchport></switchport> | ||
271 | 111 | <switchport> | ||
272 | 112 | <mode> | ||
273 | 113 | <trunk> | ||
274 | 114 | </trunk> | ||
275 | 115 | </mode> | ||
276 | 116 | </switchport> | ||
277 | 117 | </__XML__MODE_if-ethernet-switch> | ||
278 | 118 | </ethernet> | ||
279 | 119 | </interface> | ||
280 | 120 | """ | ||
281 | 121 | |||
282 | 122 | cmd_no_switchport = """ | ||
283 | 123 | <interface> | ||
284 | 124 | <ethernet> | ||
285 | 125 | <interface>%s</interface> | ||
286 | 126 | <__XML__MODE_if-ethernet-switch> | ||
287 | 127 | <no> | ||
288 | 128 | <switchport> | ||
289 | 129 | </switchport> | ||
290 | 130 | </no> | ||
291 | 131 | </__XML__MODE_if-ethernet-switch> | ||
292 | 132 | </ethernet> | ||
293 | 133 | </interface> | ||
294 | 134 | """ | ||
295 | 135 | |||
296 | 136 | |||
297 | 137 | cmd_no_vlan_int_snippet = """ | ||
298 | 138 | <interface> | ||
299 | 139 | <ethernet> | ||
300 | 140 | <interface>%s</interface> | ||
301 | 141 | <__XML__MODE_if-ethernet-switch> | ||
302 | 142 | <switchport></switchport> | ||
303 | 143 | <no> | ||
304 | 144 | <switchport> | ||
305 | 145 | <trunk> | ||
306 | 146 | <allowed> | ||
307 | 147 | <vlan> | ||
308 | 148 | <__XML__BLK_Cmd_switchport_trunk_allowed_allow-vlans> | ||
309 | 149 | <allow-vlans>%s</allow-vlans> | ||
310 | 150 | </__XML__BLK_Cmd_switchport_trunk_allowed_allow-vlans> | ||
311 | 151 | </vlan> | ||
312 | 152 | </allowed> | ||
313 | 153 | </trunk> | ||
314 | 154 | </switchport> | ||
315 | 155 | </no> | ||
316 | 156 | </__XML__MODE_if-ethernet-switch> | ||
317 | 157 | </ethernet> | ||
318 | 158 | </interface> | ||
319 | 159 | """ | ||
320 | 160 | |||
321 | 161 | |||
322 | 162 | filter_show_vlan_brief_snippet = """ | ||
323 | 163 | <show xmlns="http://www.cisco.com/nxos:1.0:vlan_mgr_cli"> | ||
324 | 164 | <vlan> | ||
325 | 165 | <brief/> | ||
326 | 166 | </vlan> | ||
327 | 167 | </show> """ | ||
328 | 168 | |||
329 | 169 | |||
330 | 170 | class CiscoNEXUSDriver(): | ||
331 | 171 | |||
332 | 172 | def __init__(self): | ||
333 | 173 | pass | ||
334 | 174 | |||
335 | 175 | def nxos_connect(self, nexus_host, port, nexus_user, nexus_password): | ||
336 | 176 | m = manager.connect(host=nexus_host, port=22, username=nexus_user, | ||
337 | 177 | password=nexus_password) | ||
338 | 178 | return m | ||
339 | 179 | |||
340 | 180 | def enable_vlan(self, mgr, vlanid, vlanname): | ||
341 | 181 | confstr = cmd_vlan_conf_snippet % (vlanid, vlanname) | ||
342 | 182 | confstr = exec_conf_prefix + confstr + exec_conf_postfix | ||
343 | 183 | mgr.edit_config(target='running', config=confstr) | ||
344 | 184 | |||
345 | 185 | def disable_vlan(self, mgr, vlanid): | ||
346 | 186 | confstr = cmd_no_vlan_conf_snippet % vlanid | ||
347 | 187 | confstr = exec_conf_prefix + confstr + exec_conf_postfix | ||
348 | 188 | mgr.edit_config(target='running', config=confstr) | ||
349 | 189 | |||
350 | 190 | def enable_port_trunk(self, mgr, interface): | ||
351 | 191 | confstr = cmd_port_trunk % (interface) | ||
352 | 192 | confstr = exec_conf_prefix + confstr + exec_conf_postfix | ||
353 | 193 | print confstr | ||
354 | 194 | mgr.edit_config(target='running', config=confstr) | ||
355 | 195 | |||
356 | 196 | def enable_vlan_on_trunk_int(self, mgr, interface, vlanid): | ||
357 | 197 | confstr = cmd_vlan_int_snippet % (interface, vlanid) | ||
358 | 198 | confstr = exec_conf_prefix + confstr + exec_conf_postfix | ||
359 | 199 | print confstr | ||
360 | 200 | mgr.edit_config(target='running', config=confstr) | ||
361 | 201 | |||
362 | 202 | def disable_vlan_on_trunk_int(self, mgr, interface, vlanid): | ||
363 | 203 | confstr = cmd_no_vlan_int_snippet % (interface, vlanid) | ||
364 | 204 | confstr = exec_conf_prefix + confstr + exec_conf_postfix | ||
365 | 205 | print confstr | ||
366 | 206 | mgr.edit_config(target='running', config=confstr) | ||
367 | 207 | |||
368 | 208 | def test_nxos_api(self, host, user, password): | ||
369 | 209 | with self.nxos_connect(host, port=22, user=user, | ||
370 | 210 | password=password) as m: | ||
371 | 211 | #enable_vlan(m, '100', 'ccn1') | ||
372 | 212 | #enable_vlan_on_trunk_int(m, '2/1', '100') | ||
373 | 213 | #disable_vlan_on_trunk_int(m, '2/1', '100') | ||
374 | 214 | #disable_vlan(m, '100') | ||
375 | 215 | result = m.get(("subtree", filter_show_vlan_brief_snippet)) | ||
376 | 216 | print result | ||
377 | 217 | |||
378 | 218 | def create_vlan(self, vlan_name, vlan_id, nexus_host, nexus_user, | ||
379 | 219 | nexus_password, nexus_interface): | ||
380 | 220 | #TODO (Edgar) Move the SSH port to the configuration file | ||
381 | 221 | with self.nxos_connect(nexus_host, 22, nexus_user, | ||
382 | 222 | nexus_password) as m: | ||
383 | 223 | self.enable_vlan(m, vlan_id, vlan_name) | ||
384 | 224 | self.enable_port_trunk(m, nexus_interface) | ||
385 | 225 | |||
386 | 226 | def delete_vlan(self, vlan_id, nexus_host, nexus_user, nexus_password): | ||
387 | 227 | with self.nxos_connect(nexus_host, 22, nexus_user, | ||
388 | 228 | nexus_password) as m: | ||
389 | 229 | self.disable_vlan(m, vlan_id) | ||
390 | 230 | |||
391 | 231 | |||
392 | 232 | def main(): | ||
393 | 233 | client = CiscoNEXUSDriver() | ||
394 | 234 | |||
395 | 235 | if __name__ == '__main__': | ||
396 | 236 | main() | ||
397 | 0 | 237 | ||
398 | === modified file 'quantum/plugins/cisco/nexus/cisco_nexus_plugin.py' | |||
399 | --- quantum/plugins/cisco/nexus/cisco_nexus_plugin.py 2011-07-31 18:38:26 +0000 | |||
400 | +++ quantum/plugins/cisco/nexus/cisco_nexus_plugin.py 2011-08-02 04:45:54 +0000 | |||
401 | @@ -15,6 +15,7 @@ | |||
402 | 15 | # under the License. | 15 | # under the License. |
403 | 16 | # | 16 | # |
404 | 17 | # @author: Sumit Naiksatam, Cisco Systems, Inc. | 17 | # @author: Sumit Naiksatam, Cisco Systems, Inc. |
405 | 18 | # @author: Edgar Magana, Cisco Systems, Inc. | ||
406 | 18 | # | 19 | # |
407 | 19 | import logging as LOG | 20 | import logging as LOG |
408 | 20 | 21 | ||
409 | @@ -25,6 +26,8 @@ | |||
410 | 25 | from quantum.plugins.cisco.common import cisco_exceptions as cexc | 26 | from quantum.plugins.cisco.common import cisco_exceptions as cexc |
411 | 26 | from quantum.plugins.cisco.common import cisco_utils as cutil | 27 | from quantum.plugins.cisco.common import cisco_utils as cutil |
412 | 27 | 28 | ||
413 | 29 | from quantum.plugins.cisco.nexus import cisco_nexus_network_driver | ||
414 | 30 | |||
415 | 28 | LOG.basicConfig(level=LOG.WARN) | 31 | LOG.basicConfig(level=LOG.WARN) |
416 | 29 | LOG.getLogger(const.LOGGER_COMPONENT_NAME) | 32 | LOG.getLogger(const.LOGGER_COMPONENT_NAME) |
417 | 30 | 33 | ||
418 | @@ -33,10 +36,12 @@ | |||
419 | 33 | _networks = {} | 36 | _networks = {} |
420 | 34 | 37 | ||
421 | 35 | def __init__(self): | 38 | def __init__(self): |
426 | 36 | """ | 39 | self._client = cisco_nexus_network_driver.CiscoNEXUSDriver() |
427 | 37 | Initialize the Nexus driver here | 40 | #TODO (Edgar) Using just one Nexus 7K Switch and Port |
428 | 38 | """ | 41 | self._nexus_ip = conf.NEXUS_IP_ADDRESS |
429 | 39 | pass | 42 | self._nexus_username = cred.Store.getUsername(conf.NEXUS_IP_ADDRESS) |
430 | 43 | self._nexus_password = cred.Store.getPassword(conf.NEXUS_IP_ADDRESS) | ||
431 | 44 | self._nexus_port = conf.NEXUS_PORT | ||
432 | 40 | 45 | ||
433 | 41 | def get_all_networks(self, tenant_id): | 46 | def get_all_networks(self, tenant_id): |
434 | 42 | """ | 47 | """ |
435 | @@ -53,8 +58,9 @@ | |||
436 | 53 | for this VLAN | 58 | for this VLAN |
437 | 54 | """ | 59 | """ |
438 | 55 | LOG.debug("NexusPlugin:create_network() called\n") | 60 | LOG.debug("NexusPlugin:create_network() called\n") |
441 | 56 | # TODO (Sumit): Call the nexus driver here to create the VLAN, and | 61 | self._client.create_vlan(vlan_name, str(vlan_id), self._nexus_ip, |
442 | 57 | # configure the appropriate interfaces | 62 | self._nexus_username, self._nexus_password, self._nexus_port) |
443 | 63 | |||
444 | 58 | new_net_dict = {const.NET_ID: net_id, | 64 | new_net_dict = {const.NET_ID: net_id, |
445 | 59 | const.NET_NAME: net_name, | 65 | const.NET_NAME: net_name, |
446 | 60 | const.NET_PORTS: {}, | 66 | const.NET_PORTS: {}, |
447 | @@ -70,9 +76,10 @@ | |||
448 | 70 | """ | 76 | """ |
449 | 71 | LOG.debug("NexusPlugin:delete_network() called\n") | 77 | LOG.debug("NexusPlugin:delete_network() called\n") |
450 | 72 | net = self._networks.get(net_id) | 78 | net = self._networks.get(net_id) |
451 | 79 | vlan_id = self._get_vlan_id_for_network(tenant_id, net_id) | ||
452 | 73 | if net: | 80 | if net: |
455 | 74 | # TODO (Sumit): Call the nexus driver here to create the VLAN, | 81 | self._client.delete_vlan(str(vlan_id), self._nexus_ip, |
456 | 75 | # and configure the appropriate interfaces | 82 | self._nexus_username, self._nexus_password) |
457 | 76 | self._networks.pop(net_id) | 83 | self._networks.pop(net_id) |
458 | 77 | return net | 84 | return net |
459 | 78 | # Network not found | 85 | # Network not found |
460 | @@ -91,6 +98,7 @@ | |||
461 | 91 | Updates the symbolic name belonging to a particular | 98 | Updates the symbolic name belonging to a particular |
462 | 92 | Virtual Network. | 99 | Virtual Network. |
463 | 93 | """ | 100 | """ |
464 | 101 | #TODO (Edgar) We need to add an update method in the Nexus Driver | ||
465 | 94 | LOG.debug("NexusPlugin:rename_network() called\n") | 102 | LOG.debug("NexusPlugin:rename_network() called\n") |
466 | 95 | network = self._get_network(tenant_id, net_id) | 103 | network = self._get_network(tenant_id, net_id) |
467 | 96 | network[const.NET_NAME] = new_name | 104 | network[const.NET_NAME] = new_name |
468 | @@ -145,6 +153,11 @@ | |||
469 | 145 | """ | 153 | """ |
470 | 146 | LOG.debug("NexusPlugin:unplug_interface() called\n") | 154 | LOG.debug("NexusPlugin:unplug_interface() called\n") |
471 | 147 | 155 | ||
472 | 156 | def _get_vlan_id_for_network(self, tenant_id, network_id): | ||
473 | 157 | net = self._get_network(tenant_id, network_id) | ||
474 | 158 | vlan_id = net[const.NET_VLAN_ID] | ||
475 | 159 | return vlan_id | ||
476 | 160 | |||
477 | 148 | def _get_network(self, tenant_id, network_id): | 161 | def _get_network(self, tenant_id, network_id): |
478 | 149 | network = self._networks.get(network_id) | 162 | network = self._networks.get(network_id) |
479 | 150 | if not network: | 163 | if not network: |
Approving the request as per Ram's suggestion.