summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorJenkins <jenkins@review.openstack.org>2013-04-12 22:53:44 +0000
committerGerrit Code Review <review@openstack.org>2013-04-12 22:53:44 +0000
commit4d5267bffcbdb0461b245d59f090a12ea6325e27 (patch)
treef2d0dbc92fda3d21d89803ce4e9466b9490b4011
parent9dc09d024e90ab8c6146815920afa7db03f04208 (diff)
parent262b285a04b00033c84f817b3f1c105afcf914cb (diff)
downloadnova-4d5267bffcbdb0461b245d59f090a12ea6325e27.tar.gz
nova-4d5267bffcbdb0461b245d59f090a12ea6325e27.tar.xz
nova-4d5267bffcbdb0461b245d59f090a12ea6325e27.zip
Merge "Add an extension to show the mac address of a ip in server(s)"
-rw-r--r--doc/api_samples/OS-EXT-IPS-MAC/server-get-resp.json55
-rw-r--r--doc/api_samples/OS-EXT-IPS-MAC/server-get-resp.xml19
-rw-r--r--doc/api_samples/OS-EXT-IPS-MAC/server-post-req.json16
-rw-r--r--doc/api_samples/OS-EXT-IPS-MAC/server-post-req.xml19
-rw-r--r--doc/api_samples/OS-EXT-IPS-MAC/server-post-resp.json16
-rw-r--r--doc/api_samples/OS-EXT-IPS-MAC/server-post-resp.xml6
-rw-r--r--doc/api_samples/OS-EXT-IPS-MAC/servers-detail-resp.json57
-rw-r--r--doc/api_samples/OS-EXT-IPS-MAC/servers-detail-resp.xml21
-rw-r--r--doc/api_samples/all_extensions/extensions-get-resp.json8
-rw-r--r--doc/api_samples/all_extensions/extensions-get-resp.xml3
-rw-r--r--doc/api_samples/all_extensions/server-get-resp.json3
-rw-r--r--doc/api_samples/all_extensions/server-get-resp.xml5
-rw-r--r--doc/api_samples/all_extensions/servers-details-resp.json3
-rw-r--r--doc/api_samples/all_extensions/servers-details-resp.xml4
-rw-r--r--etc/nova/policy.json1
-rw-r--r--nova/api/openstack/common.py20
-rw-r--r--nova/api/openstack/compute/contrib/extended_ips_mac.py110
-rw-r--r--nova/tests/api/openstack/compute/contrib/test_extended_ips_mac.py175
-rw-r--r--nova/tests/api/openstack/compute/test_extensions.py1
-rw-r--r--nova/tests/fake_policy.py1
-rw-r--r--nova/tests/integrated/api_samples/OS-EXT-IPS-MAC/server-get-resp.json.tpl55
-rw-r--r--nova/tests/integrated/api_samples/OS-EXT-IPS-MAC/server-get-resp.xml.tpl19
-rw-r--r--nova/tests/integrated/api_samples/OS-EXT-IPS-MAC/server-post-req.json.tpl16
-rw-r--r--nova/tests/integrated/api_samples/OS-EXT-IPS-MAC/server-post-req.xml.tpl19
-rw-r--r--nova/tests/integrated/api_samples/OS-EXT-IPS-MAC/server-post-resp.json.tpl16
-rw-r--r--nova/tests/integrated/api_samples/OS-EXT-IPS-MAC/server-post-resp.xml.tpl6
-rw-r--r--nova/tests/integrated/api_samples/OS-EXT-IPS-MAC/servers-detail-resp.json.tpl56
-rw-r--r--nova/tests/integrated/api_samples/OS-EXT-IPS-MAC/servers-detail-resp.xml.tpl21
-rw-r--r--nova/tests/integrated/api_samples/all_extensions/extensions-get-resp.json.tpl8
-rw-r--r--nova/tests/integrated/api_samples/all_extensions/extensions-get-resp.xml.tpl3
-rw-r--r--nova/tests/integrated/api_samples/all_extensions/server-get-resp.json.tpl3
-rw-r--r--nova/tests/integrated/api_samples/all_extensions/server-get-resp.xml.tpl5
-rw-r--r--nova/tests/integrated/api_samples/all_extensions/servers-details-resp.json.tpl3
-rw-r--r--nova/tests/integrated/api_samples/all_extensions/servers-details-resp.xml.tpl5
-rw-r--r--nova/tests/integrated/test_api_samples.py34
35 files changed, 796 insertions, 16 deletions
diff --git a/doc/api_samples/OS-EXT-IPS-MAC/server-get-resp.json b/doc/api_samples/OS-EXT-IPS-MAC/server-get-resp.json
new file mode 100644
index 000000000..50b53d810
--- /dev/null
+++ b/doc/api_samples/OS-EXT-IPS-MAC/server-get-resp.json
@@ -0,0 +1,55 @@
+{
+ "server": {
+ "accessIPv4": "",
+ "accessIPv6": "",
+ "addresses": {
+ "private": [
+ {
+ "addr": "192.168.0.3",
+ "version": 4,
+ "OS-EXT-IPS-MAC:mac_addr": "00:0c:29:e1:42:90"
+ }
+ ]
+ },
+ "created": "2013-02-07T18:46:28Z",
+ "flavor": {
+ "id": "1",
+ "links": [
+ {
+ "href": "http://openstack.example.com/openstack/flavors/1",
+ "rel": "bookmark"
+ }
+ ]
+ },
+ "hostId": "4e2003eddbfdb1280c2618d04090bcdd6773203b8da8347af0b2723d",
+ "id": "dc7281f9-ee47-40b9-9950-9f73e7961caa",
+ "image": {
+ "id": "70a599e0-31e7-49b7-b260-868f441e862b",
+ "links": [
+ {
+ "href": "http://openstack.example.com/openstack/images/70a599e0-31e7-49b7-b260-868f441e862b",
+ "rel": "bookmark"
+ }
+ ]
+ },
+ "links": [
+ {
+ "href": "http://openstack.example.com/v2/openstack/servers/dc7281f9-ee47-40b9-9950-9f73e7961caa",
+ "rel": "self"
+ },
+ {
+ "href": "http://openstack.example.com/openstack/servers/dc7281f9-ee47-40b9-9950-9f73e7961caa",
+ "rel": "bookmark"
+ }
+ ],
+ "metadata": {
+ "My Server Name": "Apache1"
+ },
+ "name": "new-server-test",
+ "progress": 0,
+ "status": "ACTIVE",
+ "tenant_id": "openstack",
+ "updated": "2013-02-07T18:46:29Z",
+ "user_id": "fake"
+ }
+}
diff --git a/doc/api_samples/OS-EXT-IPS-MAC/server-get-resp.xml b/doc/api_samples/OS-EXT-IPS-MAC/server-get-resp.xml
new file mode 100644
index 000000000..273ae36e7
--- /dev/null
+++ b/doc/api_samples/OS-EXT-IPS-MAC/server-get-resp.xml
@@ -0,0 +1,19 @@
+<?xml version='1.0' encoding='UTF-8'?>
+<server xmlns:OS-EXT-IPS-MAC="http://docs.openstack.org/compute/ext/extended_ips_mac/api/v1.1" xmlns:atom="http://www.w3.org/2005/Atom" xmlns="http://docs.openstack.org/compute/api/v1.1" status="ACTIVE" updated="2013-02-07T18:46:29Z" hostId="068cc5e2de14b6e533a239c6eac0a0bdedcd57cab25450a6d3da43af" name="new-server-test" created="2013-02-07T18:46:28Z" userId="fake" tenantId="openstack" accessIPv4="" accessIPv6="" progress="0" id="22e7cf4d-ab7a-4a3d-9599-7d0dbaf9ed55">
+ <image id="70a599e0-31e7-49b7-b260-868f441e862b">
+ <atom:link href="http://openstack.example.com/openstack/images/70a599e0-31e7-49b7-b260-868f441e862b" rel="bookmark"/>
+ </image>
+ <flavor id="1">
+ <atom:link href="http://openstack.example.com/openstack/flavors/1" rel="bookmark"/>
+ </flavor>
+ <metadata>
+ <meta key="My Server Name">Apache1</meta>
+ </metadata>
+ <addresses>
+ <network id="private">
+ <ip version="4" addr="192.168.0.3" OS-EXT-IPS-MAC:mac_addr="00:0c:29:e1:42:90"/>
+ </network>
+ </addresses>
+ <atom:link href="http://openstack.example.com/v2/openstack/servers/22e7cf4d-ab7a-4a3d-9599-7d0dbaf9ed55" rel="self"/>
+ <atom:link href="http://openstack.example.com/openstack/servers/22e7cf4d-ab7a-4a3d-9599-7d0dbaf9ed55" rel="bookmark"/>
+</server>
diff --git a/doc/api_samples/OS-EXT-IPS-MAC/server-post-req.json b/doc/api_samples/OS-EXT-IPS-MAC/server-post-req.json
new file mode 100644
index 000000000..d88eb4122
--- /dev/null
+++ b/doc/api_samples/OS-EXT-IPS-MAC/server-post-req.json
@@ -0,0 +1,16 @@
+{
+ "server" : {
+ "name" : "new-server-test",
+ "imageRef" : "http://openstack.example.com/openstack/images/70a599e0-31e7-49b7-b260-868f441e862b",
+ "flavorRef" : "http://openstack.example.com/openstack/flavors/1",
+ "metadata" : {
+ "My Server Name" : "Apache1"
+ },
+ "personality" : [
+ {
+ "path" : "/etc/banner.txt",
+ "contents" : "ICAgICAgDQoiQSBjbG91ZCBkb2VzIG5vdCBrbm93IHdoeSBpdCBtb3ZlcyBpbiBqdXN0IHN1Y2ggYSBkaXJlY3Rpb24gYW5kIGF0IHN1Y2ggYSBzcGVlZC4uLkl0IGZlZWxzIGFuIGltcHVsc2lvbi4uLnRoaXMgaXMgdGhlIHBsYWNlIHRvIGdvIG5vdy4gQnV0IHRoZSBza3kga25vd3MgdGhlIHJlYXNvbnMgYW5kIHRoZSBwYXR0ZXJucyBiZWhpbmQgYWxsIGNsb3VkcywgYW5kIHlvdSB3aWxsIGtub3csIHRvbywgd2hlbiB5b3UgbGlmdCB5b3Vyc2VsZiBoaWdoIGVub3VnaCB0byBzZWUgYmV5b25kIGhvcml6b25zLiINCg0KLVJpY2hhcmQgQmFjaA=="
+ }
+ ]
+ }
+} \ No newline at end of file
diff --git a/doc/api_samples/OS-EXT-IPS-MAC/server-post-req.xml b/doc/api_samples/OS-EXT-IPS-MAC/server-post-req.xml
new file mode 100644
index 000000000..0a3c8bb53
--- /dev/null
+++ b/doc/api_samples/OS-EXT-IPS-MAC/server-post-req.xml
@@ -0,0 +1,19 @@
+<?xml version="1.0" encoding="UTF-8"?>
+<server xmlns="http://docs.openstack.org/compute/api/v1.1" imageRef="http://openstack.example.com/openstack/images/70a599e0-31e7-49b7-b260-868f441e862b" flavorRef="http://openstack.example.com/openstack/flavors/1" name="new-server-test">
+ <metadata>
+ <meta key="My Server Name">Apache1</meta>
+ </metadata>
+ <personality>
+ <file path="/etc/banner.txt">
+ ICAgICAgDQoiQSBjbG91ZCBkb2VzIG5vdCBrbm93IHdoeSBp
+ dCBtb3ZlcyBpbiBqdXN0IHN1Y2ggYSBkaXJlY3Rpb24gYW5k
+ IGF0IHN1Y2ggYSBzcGVlZC4uLkl0IGZlZWxzIGFuIGltcHVs
+ c2lvbi4uLnRoaXMgaXMgdGhlIHBsYWNlIHRvIGdvIG5vdy4g
+ QnV0IHRoZSBza3kga25vd3MgdGhlIHJlYXNvbnMgYW5kIHRo
+ ZSBwYXR0ZXJucyBiZWhpbmQgYWxsIGNsb3VkcywgYW5kIHlv
+ dSB3aWxsIGtub3csIHRvbywgd2hlbiB5b3UgbGlmdCB5b3Vy
+ c2VsZiBoaWdoIGVub3VnaCB0byBzZWUgYmV5b25kIGhvcml6
+ b25zLiINCg0KLVJpY2hhcmQgQmFjaA==
+ </file>
+ </personality>
+</server> \ No newline at end of file
diff --git a/doc/api_samples/OS-EXT-IPS-MAC/server-post-resp.json b/doc/api_samples/OS-EXT-IPS-MAC/server-post-resp.json
new file mode 100644
index 000000000..d641e74aa
--- /dev/null
+++ b/doc/api_samples/OS-EXT-IPS-MAC/server-post-resp.json
@@ -0,0 +1,16 @@
+{
+ "server": {
+ "adminPass": "zD7wDKTXiHsp",
+ "id": "b44e5008-42f7-4048-b4c8-f40a29da88ba",
+ "links": [
+ {
+ "href": "http://openstack.example.com/v2/openstack/servers/b44e5008-42f7-4048-b4c8-f40a29da88ba",
+ "rel": "self"
+ },
+ {
+ "href": "http://openstack.example.com/openstack/servers/b44e5008-42f7-4048-b4c8-f40a29da88ba",
+ "rel": "bookmark"
+ }
+ ]
+ }
+} \ No newline at end of file
diff --git a/doc/api_samples/OS-EXT-IPS-MAC/server-post-resp.xml b/doc/api_samples/OS-EXT-IPS-MAC/server-post-resp.xml
new file mode 100644
index 000000000..b268ba0d3
--- /dev/null
+++ b/doc/api_samples/OS-EXT-IPS-MAC/server-post-resp.xml
@@ -0,0 +1,6 @@
+<?xml version='1.0' encoding='UTF-8'?>
+<server xmlns:atom="http://www.w3.org/2005/Atom" xmlns="http://docs.openstack.org/compute/api/v1.1" id="752dd57d-933b-4a57-a0ae-4c3431c5abc7" adminPass="B2gvFFjBQCVQ">
+ <metadata/>
+ <atom:link href="http://openstack.example.com/v2/openstack/servers/752dd57d-933b-4a57-a0ae-4c3431c5abc7" rel="self"/>
+ <atom:link href="http://openstack.example.com/openstack/servers/752dd57d-933b-4a57-a0ae-4c3431c5abc7" rel="bookmark"/>
+</server> \ No newline at end of file
diff --git a/doc/api_samples/OS-EXT-IPS-MAC/servers-detail-resp.json b/doc/api_samples/OS-EXT-IPS-MAC/servers-detail-resp.json
new file mode 100644
index 000000000..115780401
--- /dev/null
+++ b/doc/api_samples/OS-EXT-IPS-MAC/servers-detail-resp.json
@@ -0,0 +1,57 @@
+{
+ "servers": [
+ {
+ "accessIPv4": "",
+ "accessIPv6": "",
+ "addresses": {
+ "private": [
+ {
+ "addr": "192.168.0.3",
+ "version": 4,
+ "OS-EXT-IPS-MAC:mac_addr": "00:0c:29:e1:42:90"
+ }
+ ]
+ },
+ "created": "2013-02-07T18:40:59Z",
+ "flavor": {
+ "id": "1",
+ "links": [
+ {
+ "href": "http://openstack.example.com/openstack/flavors/1",
+ "rel": "bookmark"
+ }
+ ]
+ },
+ "hostId": "fe866a4962fe3bdb6c2db9c8f7dcdb9555aca73387e72b5cb9c45bd3",
+ "id": "76908712-653a-4d16-807e-d89d41435d24",
+ "image": {
+ "id": "70a599e0-31e7-49b7-b260-868f441e862b",
+ "links": [
+ {
+ "href": "http://openstack.example.com/openstack/images/70a599e0-31e7-49b7-b260-868f441e862b",
+ "rel": "bookmark"
+ }
+ ]
+ },
+ "links": [
+ {
+ "href": "http://openstack.example.com/v2/openstack/servers/76908712-653a-4d16-807e-d89d41435d24",
+ "rel": "self"
+ },
+ {
+ "href": "http://openstack.example.com/openstack/servers/76908712-653a-4d16-807e-d89d41435d24",
+ "rel": "bookmark"
+ }
+ ],
+ "metadata": {
+ "My Server Name": "Apache1"
+ },
+ "name": "new-server-test",
+ "progress": 0,
+ "status": "ACTIVE",
+ "tenant_id": "openstack",
+ "updated": "2013-02-07T18:40:59Z",
+ "user_id": "fake"
+ }
+ ]
+}
diff --git a/doc/api_samples/OS-EXT-IPS-MAC/servers-detail-resp.xml b/doc/api_samples/OS-EXT-IPS-MAC/servers-detail-resp.xml
new file mode 100644
index 000000000..c2f958a14
--- /dev/null
+++ b/doc/api_samples/OS-EXT-IPS-MAC/servers-detail-resp.xml
@@ -0,0 +1,21 @@
+<?xml version='1.0' encoding='UTF-8'?>
+<servers xmlns:OS-EXT-IPS-MAC="http://docs.openstack.org/compute/ext/extended_ips_mac/api/v1.1" xmlns:atom="http://www.w3.org/2005/Atom" xmlns="http://docs.openstack.org/compute/api/v1.1">
+ <server status="ACTIVE" updated="2013-02-07T18:40:59Z" hostId="51a80e6ee89b638b2cb57eb4e39d89a725e07c8a698f4d8e256f8665" name="new-server-test" created="2013-02-07T18:40:59Z" userId="fake" tenantId="openstack" accessIPv4="" accessIPv6="" progress="0" id="0337de6b-1d43-46c8-8804-35669f1dea9a">
+ <image id="70a599e0-31e7-49b7-b260-868f441e862b">
+ <atom:link href="http://openstack.example.com/openstack/images/70a599e0-31e7-49b7-b260-868f441e862b" rel="bookmark"/>
+ </image>
+ <flavor id="1">
+ <atom:link href="http://openstack.example.com/openstack/flavors/1" rel="bookmark"/>
+ </flavor>
+ <metadata>
+ <meta key="My Server Name">Apache1</meta>
+ </metadata>
+ <addresses>
+ <network id="private">
+ <ip version="4" addr="192.168.0.3" OS-EXT-IPS-MAC:mac_addr="00:0c:29:e1:42:90"/>
+ </network>
+ </addresses>
+ <atom:link href="http://openstack.example.com/v2/openstack/servers/0337de6b-1d43-46c8-8804-35669f1dea9a" rel="self"/>
+ <atom:link href="http://openstack.example.com/openstack/servers/0337de6b-1d43-46c8-8804-35669f1dea9a" rel="bookmark"/>
+ </server>
+</servers>
diff --git a/doc/api_samples/all_extensions/extensions-get-resp.json b/doc/api_samples/all_extensions/extensions-get-resp.json
index 4fcf47fe5..df8ed83e5 100644
--- a/doc/api_samples/all_extensions/extensions-get-resp.json
+++ b/doc/api_samples/all_extensions/extensions-get-resp.json
@@ -41,6 +41,14 @@
"updated": "2013-01-06T00:00:00+00:00"
},
{
+ "alias": "OS-EXT-IPS-MAC",
+ "description": "Adds mac address parameter to the ip list.",
+ "links": [],
+ "name": "ExtendedIpsMac",
+ "namespace": "http://docs.openstack.org/compute/ext/extended_ips_mac/api/v1.1",
+ "updated": "2013-03-07T00:00:00+00:00"
+ },
+ {
"alias": "OS-EXT-SRV-ATTR",
"description": "Extended Server Attributes support.",
"links": [],
diff --git a/doc/api_samples/all_extensions/extensions-get-resp.xml b/doc/api_samples/all_extensions/extensions-get-resp.xml
index 179a05363..1ec2010dc 100644
--- a/doc/api_samples/all_extensions/extensions-get-resp.xml
+++ b/doc/api_samples/all_extensions/extensions-get-resp.xml
@@ -15,6 +15,9 @@
<extension alias="OS-EXT-IPS" updated="2013-01-06T00:00:00+00:00" namespace="http://docs.openstack.org/compute/ext/extended_ips/api/v1.1" name="ExtendedIps">
<description>Adds type parameter to the ip list.</description>
</extension>
+ <extension alias="OS-EXT-IPS-MAC" updated="2013-03-07T00:00:00+00:00" namespace="http://docs.openstack.org/compute/ext/extended_ips_mac/api/v1.1" name="ExtendedIpsMac">
+ <description>Adds mac address parameter to the ip list.</description>
+ </extension>
<extension alias="OS-EXT-SRV-ATTR" updated="2011-11-03T00:00:00+00:00" namespace="http://docs.openstack.org/compute/ext/extended_status/api/v1.1" name="ExtendedServerAttributes">
<description>Extended Server Attributes support.</description>
</extension>
diff --git a/doc/api_samples/all_extensions/server-get-resp.json b/doc/api_samples/all_extensions/server-get-resp.json
index 63f955ed6..67a33cab1 100644
--- a/doc/api_samples/all_extensions/server-get-resp.json
+++ b/doc/api_samples/all_extensions/server-get-resp.json
@@ -15,7 +15,8 @@
{
"OS-EXT-IPS:type": "fixed",
"addr": "192.168.0.3",
- "version": 4
+ "version": 4,
+ "OS-EXT-IPS-MAC:mac_addr": "00:0c:29:e1:42:90"
}
]
},
diff --git a/doc/api_samples/all_extensions/server-get-resp.xml b/doc/api_samples/all_extensions/server-get-resp.xml
index e2ded16e5..6db40414b 100644
--- a/doc/api_samples/all_extensions/server-get-resp.xml
+++ b/doc/api_samples/all_extensions/server-get-resp.xml
@@ -1,5 +1,5 @@
<?xml version='1.0' encoding='UTF-8'?>
-<server xmlns:OS-DCF="http://docs.openstack.org/compute/ext/disk_config/api/v1.1" xmlns:atom="http://www.w3.org/2005/Atom" xmlns:OS-EXT-SRV-ATTR="http://docs.openstack.org/compute/ext/extended_status/api/v1.1" xmlns:OS-EXT-IPS="http://docs.openstack.org/compute/ext/extended_ips/api/v1.1" xmlns:OS-EXT-STS="http://docs.openstack.org/compute/ext/extended_status/api/v1.1" xmlns:OS-EXT-AZ="http://docs.openstack.org/compute/ext/extended_availability_zone/api/v2" xmlns="http://docs.openstack.org/compute/api/v1.1" status="ACTIVE" updated="2013-02-07T19:01:59Z" hostId="06d1cfd52be5f5d197193db2842978235fd085bd2dfaea32e5068468" name="new-server-test" created="2013-02-07T19:01:58Z" userId="fake" tenantId="openstack" accessIPv4="" accessIPv6="" progress="0" id="6be39927-53b2-4aee-8593-1c72b3673168" key_name="None" config_drive="" OS-EXT-SRV-ATTR:vm_state="active" OS-EXT-SRV-ATTR:task_state="None" OS-EXT-SRV-ATTR:power_state="1" OS-EXT-SRV-ATTR:instance_name="instance-00000001" OS-EXT-SRV-ATTR:host="b98603db318e495e819601702d16c512" OS-EXT-SRV-ATTR:hypervisor_hostname="fake-mini" OS-EXT-AZ:availability_zone="nova" OS-DCF:diskConfig="AUTO">
+<server xmlns:OS-DCF="http://docs.openstack.org/compute/ext/disk_config/api/v1.1" xmlns:atom="http://www.w3.org/2005/Atom" xmlns:OS-EXT-SRV-ATTR="http://docs.openstack.org/compute/ext/extended_status/api/v1.1" xmlns:OS-EXT-IPS="http://docs.openstack.org/compute/ext/extended_ips/api/v1.1" xmlns:OS-EXT-IPS-MAC="http://docs.openstack.org/compute/ext/extended_ips_mac/api/v1.1" xmlns:OS-EXT-STS="http://docs.openstack.org/compute/ext/extended_status/api/v1.1" xmlns:OS-EXT-AZ="http://docs.openstack.org/compute/ext/extended_availability_zone/api/v2" xmlns="http://docs.openstack.org/compute/api/v1.1" status="ACTIVE" updated="2013-02-07T19:01:59Z" hostId="06d1cfd52be5f5d197193db2842978235fd085bd2dfaea32e5068468" name="new-server-test" created="2013-02-07T19:01:58Z" userId="fake" tenantId="openstack" accessIPv4="" accessIPv6="" progress="0" id="6be39927-53b2-4aee-8593-1c72b3673168" key_name="None" config_drive="" OS-EXT-SRV-ATTR:vm_state="active" OS-EXT-SRV-ATTR:task_state="None" OS-EXT-SRV-ATTR:power_state="1" OS-EXT-SRV-ATTR:instance_name="instance-00000001" OS-EXT-SRV-ATTR:host="b98603db318e495e819601702d16c512" OS-EXT-SRV-ATTR:hypervisor_hostname="fake-mini" OS-EXT-AZ:availability_zone="nova" OS-DCF:diskConfig="AUTO">
<image id="70a599e0-31e7-49b7-b260-868f441e862b">
<atom:link href="http://openstack.example.com/openstack/images/70a599e0-31e7-49b7-b260-868f441e862b" rel="bookmark"/>
</image>
@@ -11,7 +11,8 @@
</metadata>
<addresses>
<network id="private">
- <ip OS-EXT-IPS:type="fixed" version="4" addr="192.168.0.3"/>
+ <ip OS-EXT-IPS:type="fixed" version="4" addr="192.168.0.3"
+ OS-EXT-IPS-MAC:mac_addr="00:0c:29:e1:42:90"/>
</network>
</addresses>
<atom:link href="http://openstack.example.com/v2/openstack/servers/6be39927-53b2-4aee-8593-1c72b3673168" rel="self"/>
diff --git a/doc/api_samples/all_extensions/servers-details-resp.json b/doc/api_samples/all_extensions/servers-details-resp.json
index cc945edb5..05f11a246 100644
--- a/doc/api_samples/all_extensions/servers-details-resp.json
+++ b/doc/api_samples/all_extensions/servers-details-resp.json
@@ -16,7 +16,8 @@
{
"OS-EXT-IPS:type": "fixed",
"addr": "192.168.0.3",
- "version": 4
+ "version": 4,
+ "OS-EXT-IPS-MAC:mac_addr": "00:0c:29:e1:42:90"
}
]
},
diff --git a/doc/api_samples/all_extensions/servers-details-resp.xml b/doc/api_samples/all_extensions/servers-details-resp.xml
index 44b3b09c5..8061caf21 100644
--- a/doc/api_samples/all_extensions/servers-details-resp.xml
+++ b/doc/api_samples/all_extensions/servers-details-resp.xml
@@ -1,5 +1,5 @@
<?xml version='1.0' encoding='UTF-8'?>
-<servers xmlns:OS-DCF="http://docs.openstack.org/compute/ext/disk_config/api/v1.1" xmlns:atom="http://www.w3.org/2005/Atom" xmlns:OS-EXT-SRV-ATTR="http://docs.openstack.org/compute/ext/extended_status/api/v1.1" xmlns:OS-EXT-IPS="http://docs.openstack.org/compute/ext/extended_ips/api/v1.1" xmlns:OS-EXT-STS="http://docs.openstack.org/compute/ext/extended_status/api/v1.1" xmlns:OS-EXT-AZ="http://docs.openstack.org/compute/ext/extended_availability_zone/api/v2" xmlns="http://docs.openstack.org/compute/api/v1.1">
+<servers xmlns:OS-DCF="http://docs.openstack.org/compute/ext/disk_config/api/v1.1" xmlns:atom="http://www.w3.org/2005/Atom" xmlns:OS-EXT-SRV-ATTR="http://docs.openstack.org/compute/ext/extended_status/api/v1.1" xmlns:OS-EXT-IPS="http://docs.openstack.org/compute/ext/extended_ips/api/v1.1" xmlns:OS-EXT-IPS-MAC="http://docs.openstack.org/compute/ext/extended_ips_mac/api/v1.1" xmlns:OS-EXT-STS="http://docs.openstack.org/compute/ext/extended_status/api/v1.1" xmlns:OS-EXT-AZ="http://docs.openstack.org/compute/ext/extended_availability_zone/api/v2" xmlns="http://docs.openstack.org/compute/api/v1.1">
<server status="ACTIVE" updated="2013-02-07T19:01:59Z" hostId="641edaad8dd6a670afec58a4ce7e908d50379a6060f845236cd063db" name="new-server-test" created="2013-02-07T19:01:58Z" userId="fake" tenantId="openstack" accessIPv4="" accessIPv6="" progress="0" id="b45edf9d-30f6-41e8-a00b-ef8962376586" key_name="None" config_drive="" OS-EXT-SRV-ATTR:vm_state="active" OS-EXT-SRV-ATTR:task_state="None" OS-EXT-SRV-ATTR:power_state="1" OS-EXT-SRV-ATTR:instance_name="instance-00000001" OS-EXT-SRV-ATTR:host="f7954cfa4a5544278876b1d9224efe48" OS-EXT-SRV-ATTR:hypervisor_hostname="fake-mini" OS-EXT-AZ:availability_zone="nova" OS-DCF:diskConfig="AUTO">
<image id="70a599e0-31e7-49b7-b260-868f441e862b">
<atom:link href="http://openstack.example.com/openstack/images/70a599e0-31e7-49b7-b260-868f441e862b" rel="bookmark"/>
@@ -12,7 +12,7 @@
</metadata>
<addresses>
<network id="private">
- <ip OS-EXT-IPS:type="fixed" version="4" addr="192.168.0.3"/>
+ <ip OS-EXT-IPS:type="fixed" version="4" addr="192.168.0.3" OS-EXT-IPS-MAC:mac_addr="00:0c:29:e1:42:90"/>
</network>
</addresses>
<atom:link href="http://openstack.example.com/v2/openstack/servers/b45edf9d-30f6-41e8-a00b-ef8962376586" rel="self"/>
diff --git a/etc/nova/policy.json b/etc/nova/policy.json
index 1213f3fb5..26a227ae2 100644
--- a/etc/nova/policy.json
+++ b/etc/nova/policy.json
@@ -46,6 +46,7 @@
"compute_extension:extended_status": "",
"compute_extension:extended_availability_zone": "",
"compute_extension:extended_ips": "",
+ "compute_extension:extended_ips_mac": "",
"compute_extension:extended_vif_net": "",
"compute_extension:fixed_ips": "rule:admin_api",
"compute_extension:flavor_access": "",
diff --git a/nova/api/openstack/common.py b/nova/api/openstack/common.py
index 6e3d7eabc..24250c0af 100644
--- a/nova/api/openstack/common.py
+++ b/nova/api/openstack/common.py
@@ -16,6 +16,7 @@
# under the License.
import functools
+import itertools
import os
import re
import urlparse
@@ -320,6 +321,9 @@ def get_networks_for_instance_from_nw_info(nw_info):
networks[label]['ips'].extend(ips)
networks[label]['floating_ips'].extend(floaters)
+ for ip in itertools.chain(networks[label]['ips'],
+ networks[label]['floating_ips']):
+ ip['mac_address'] = vif['address']
return networks
@@ -328,10 +332,18 @@ def get_networks_for_instance(context, instance):
We end up with a data structure like::
- {'public': {'ips': [{'addr': '10.0.0.1', 'version': 4},
- {'addr': '2001::1', 'version': 6}],
- 'floating_ips': [{'addr': '172.16.0.1', 'version': 4},
- {'addr': '172.16.2.1', 'version': 4}]},
+ {'public': {'ips': [{'address': '10.0.0.1',
+ 'version': 4,
+ 'mac_address': 'aa:aa:aa:aa:aa:aa'},
+ {'address': '2001::1',
+ 'version': 6,
+ 'mac_address': 'aa:aa:aa:aa:aa:aa'}],
+ 'floating_ips': [{'address': '172.16.0.1',
+ 'version': 4,
+ 'mac_address': 'aa:aa:aa:aa:aa:aa'},
+ {'address': '172.16.2.1',
+ 'version': 4,
+ 'mac_address': 'aa:aa:aa:aa:aa:aa'}]},
...}
"""
nw_info = compute_utils.get_nw_info_for_instance(instance)
diff --git a/nova/api/openstack/compute/contrib/extended_ips_mac.py b/nova/api/openstack/compute/contrib/extended_ips_mac.py
new file mode 100644
index 000000000..a577513fd
--- /dev/null
+++ b/nova/api/openstack/compute/contrib/extended_ips_mac.py
@@ -0,0 +1,110 @@
+# vim: tabstop=4 shiftwidth=4 softtabstop=4
+
+# Copyright 2013 IBM Corp.
+#
+# 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.
+
+"""The Extended Ips API extension."""
+
+import itertools
+
+from nova.api.openstack import common
+from nova.api.openstack.compute import ips
+from nova.api.openstack import extensions
+from nova.api.openstack import wsgi
+from nova.api.openstack import xmlutil
+from nova.openstack.common import log as logging
+
+LOG = logging.getLogger(__name__)
+authorize = extensions.soft_extension_authorizer('compute', 'extended_ips_mac')
+
+
+class ExtendedIpsMacController(wsgi.Controller):
+ def __init__(self, *args, **kwargs):
+ super(ExtendedIpsMacController, self).__init__(*args, **kwargs)
+
+ def _extend_server(self, context, server, instance):
+ key = "%s:mac_addr" % Extended_ips_mac.alias
+ networks = common.get_networks_for_instance(context, instance)
+ for label, network in networks.items():
+ # NOTE(vish): ips are hidden in some states via the
+ # hide_server_addresses extension.
+ if label in server['addresses']:
+ all_ips = itertools.chain(network["ips"],
+ network["floating_ips"])
+ for i, ip in enumerate(all_ips):
+ server['addresses'][label][i][key] = ip['mac_address']
+
+ @wsgi.extends
+ def show(self, req, resp_obj, id):
+ context = req.environ['nova.context']
+ if authorize(context):
+ # Attach our slave template to the response object
+ resp_obj.attach(xml=ExtendedIpsMacServerTemplate())
+ server = resp_obj.obj['server']
+ db_instance = req.get_db_instance(server['id'])
+ # server['id'] is guaranteed to be in the cache due to
+ # the core API adding it in its 'show' method.
+ self._extend_server(context, server, db_instance)
+
+ @wsgi.extends
+ def detail(self, req, resp_obj):
+ context = req.environ['nova.context']
+ if authorize(context):
+ # Attach our slave template to the response object
+ resp_obj.attach(xml=ExtendedIpsMacServersTemplate())
+ servers = list(resp_obj.obj['servers'])
+ for server in servers:
+ db_instance = req.get_db_instance(server['id'])
+ # server['id'] is guaranteed to be in the cache due to
+ # the core API adding it in its 'detail' method.
+ self._extend_server(context, server, db_instance)
+
+
+class Extended_ips_mac(extensions.ExtensionDescriptor):
+ """Adds mac address parameter to the ip list."""
+
+ name = "ExtendedIpsMac"
+ alias = "OS-EXT-IPS-MAC"
+ namespace = ("http://docs.openstack.org/compute/ext/"
+ "extended_ips_mac/api/v1.1")
+ updated = "2013-03-07T00:00:00+00:00"
+
+ def get_controller_extensions(self):
+ controller = ExtendedIpsMacController()
+ extension = extensions.ControllerExtension(self, 'servers', controller)
+ return [extension]
+
+
+def make_server(elem):
+ elem.append(ips.AddressesTemplate())
+ ip = elem['addresses']['network']['ip']
+ ip.set('{%s}mac_addr' % Extended_ips_mac.namespace,
+ '%s:mac_addr' % Extended_ips_mac.alias)
+
+
+class ExtendedIpsMacServerTemplate(xmlutil.TemplateBuilder):
+ def construct(self):
+ root = xmlutil.TemplateElement('server', selector='server')
+ make_server(root)
+ return xmlutil.SlaveTemplate(root, 1, nsmap={
+ Extended_ips_mac.alias: Extended_ips_mac.namespace})
+
+
+class ExtendedIpsMacServersTemplate(xmlutil.TemplateBuilder):
+ def construct(self):
+ root = xmlutil.TemplateElement('servers')
+ elem = xmlutil.SubTemplateElement(root, 'server', selector='servers')
+ make_server(elem)
+ return xmlutil.SlaveTemplate(root, 1, nsmap={
+ Extended_ips_mac.alias: Extended_ips_mac.namespace})
diff --git a/nova/tests/api/openstack/compute/contrib/test_extended_ips_mac.py b/nova/tests/api/openstack/compute/contrib/test_extended_ips_mac.py
new file mode 100644
index 000000000..0bbbc9cc8
--- /dev/null
+++ b/nova/tests/api/openstack/compute/contrib/test_extended_ips_mac.py
@@ -0,0 +1,175 @@
+# vim: tabstop=4 shiftwidth=4 softtabstop=4
+
+# Copyright 2013 IBM Corp.
+# 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 lxml import etree
+import webob
+
+from nova.api.openstack.compute.contrib import extended_ips_mac
+from nova.api.openstack import xmlutil
+from nova import compute
+from nova.openstack.common import jsonutils
+from nova import test
+from nova.tests.api.openstack import fakes
+
+UUID1 = '00000000-0000-0000-0000-000000000001'
+UUID2 = '00000000-0000-0000-0000-000000000002'
+UUID3 = '00000000-0000-0000-0000-000000000003'
+NW_CACHE = [
+ {
+ 'address': 'aa:aa:aa:aa:aa:aa',
+ 'id': 1,
+ 'network': {
+ 'bridge': 'br0',
+ 'id': 1,
+ 'label': 'private',
+ 'subnets': [
+ {
+ 'cidr': '192.168.1.0/24',
+ 'ips': [
+ {
+ 'address': '192.168.1.100',
+ 'type': 'fixed',
+ 'floating_ips': [
+ {'address': '5.0.0.1', 'type': 'floating'},
+ ],
+ },
+ ],
+ },
+ ]
+ }
+ },
+ {
+ 'address': 'bb:bb:bb:bb:bb:bb',
+ 'id': 2,
+ 'network': {
+ 'bridge': 'br1',
+ 'id': 2,
+ 'label': 'public',
+ 'subnets': [
+ {
+ 'cidr': '10.0.0.0/24',
+ 'ips': [
+ {
+ 'address': '10.0.0.100',
+ 'type': 'fixed',
+ 'floating_ips': [
+ {'address': '5.0.0.2', 'type': 'floating'},
+ ],
+ }
+ ],
+ },
+ ]
+ }
+ }
+]
+ALL_IPS = []
+for cache in NW_CACHE:
+ for subnet in cache['network']['subnets']:
+ for fixed in subnet['ips']:
+ sanitized = dict(fixed)
+ sanitized['mac_address'] = cache['address']
+ sanitized.pop('floating_ips')
+ sanitized.pop('type')
+ ALL_IPS.append(sanitized)
+ for floating in fixed['floating_ips']:
+ sanitized = dict(floating)
+ sanitized['mac_address'] = cache['address']
+ sanitized.pop('type')
+ ALL_IPS.append(sanitized)
+ALL_IPS.sort()
+
+
+def fake_compute_get(*args, **kwargs):
+ return fakes.stub_instance(1, uuid=UUID3, nw_cache=NW_CACHE)
+
+
+def fake_compute_get_all(*args, **kwargs):
+ return [
+ fakes.stub_instance(1, uuid=UUID1, nw_cache=NW_CACHE),
+ fakes.stub_instance(2, uuid=UUID2, nw_cache=NW_CACHE),
+ ]
+
+
+class ExtendedIpsMacTest(test.TestCase):
+ content_type = 'application/json'
+ prefix = '%s:' % extended_ips_mac.Extended_ips_mac.alias
+
+ def setUp(self):
+ super(ExtendedIpsMacTest, self).setUp()
+ fakes.stub_out_nw_api(self.stubs)
+ self.stubs.Set(compute.api.API, 'get', fake_compute_get)
+ self.stubs.Set(compute.api.API, 'get_all', fake_compute_get_all)
+ self.flags(
+ osapi_compute_extension=[
+ 'nova.api.openstack.compute.contrib.select_extensions'],
+ osapi_compute_ext_list=['Extended_ips_mac'])
+
+ def _make_request(self, url):
+ req = webob.Request.blank(url)
+ req.headers['Accept'] = self.content_type
+ res = req.get_response(fakes.wsgi_app(init_only=('servers',)))
+ return res
+
+ def _get_server(self, body):
+ return jsonutils.loads(body).get('server')
+
+ def _get_servers(self, body):
+ return jsonutils.loads(body).get('servers')
+
+ def _get_ips(self, server):
+ for network in server['addresses'].itervalues():
+ for ip in network:
+ yield ip
+
+ def assertServerStates(self, server):
+ results = []
+ for ip in self._get_ips(server):
+ results.append({'address': ip.get('addr'),
+ 'mac_address': ip.get('%smac_addr' % self.prefix)})
+
+ self.assertEqual(ALL_IPS, sorted(results))
+
+ def test_show(self):
+ url = '/v2/fake/servers/%s' % UUID3
+ res = self._make_request(url)
+
+ self.assertEqual(res.status_int, 200)
+ self.assertServerStates(self._get_server(res.body))
+
+ def test_detail(self):
+ url = '/v2/fake/servers/detail'
+ res = self._make_request(url)
+
+ self.assertEqual(res.status_int, 200)
+ for _i, server in enumerate(self._get_servers(res.body)):
+ self.assertServerStates(server)
+
+
+class ExtendedIpsMacXmlTest(ExtendedIpsMacTest):
+ content_type = 'application/xml'
+ prefix = '{%s}' % extended_ips_mac.Extended_ips_mac.namespace
+
+ def _get_server(self, body):
+ return etree.XML(body)
+
+ def _get_servers(self, body):
+ return etree.XML(body).getchildren()
+
+ def _get_ips(self, server):
+ for network in server.find('{%s}addresses' % xmlutil.XMLNS_V11):
+ for ip in network:
+ yield ip
diff --git a/nova/tests/api/openstack/compute/test_extensions.py b/nova/tests/api/openstack/compute/test_extensions.py
index e73d42ad7..658d0c474 100644
--- a/nova/tests/api/openstack/compute/test_extensions.py
+++ b/nova/tests/api/openstack/compute/test_extensions.py
@@ -168,6 +168,7 @@ class ExtensionControllerTest(ExtensionTestCase):
"DiskConfig",
"ExtendedAvailabilityZone",
"ExtendedIps",
+ "ExtendedIpsMac",
"ExtendedVIFNet",
"Evacuate",
"ExtendedStatus",
diff --git a/nova/tests/fake_policy.py b/nova/tests/fake_policy.py
index c0bbe9467..b87360d0e 100644
--- a/nova/tests/fake_policy.py
+++ b/nova/tests/fake_policy.py
@@ -124,6 +124,7 @@ policy_data = """
"compute_extension:extended_status": "",
"compute_extension:extended_availability_zone": "",
"compute_extension:extended_ips": "",
+ "compute_extension:extended_ips_mac": "",
"compute_extension:extended_vif_net": "",
"compute_extension:fixed_ips": "",
"compute_extension:flavor_access": "",
diff --git a/nova/tests/integrated/api_samples/OS-EXT-IPS-MAC/server-get-resp.json.tpl b/nova/tests/integrated/api_samples/OS-EXT-IPS-MAC/server-get-resp.json.tpl
new file mode 100644
index 000000000..600a063c3
--- /dev/null
+++ b/nova/tests/integrated/api_samples/OS-EXT-IPS-MAC/server-get-resp.json.tpl
@@ -0,0 +1,55 @@
+{
+ "server": {
+ "accessIPv4": "",
+ "accessIPv6": "",
+ "addresses": {
+ "private": [
+ {
+ "addr": "%(ip)s",
+ "version": 4,
+ "OS-EXT-IPS-MAC:mac_addr": "%(mac_addr)s"
+ }
+ ]
+ },
+ "created": "%(timestamp)s",
+ "flavor": {
+ "id": "1",
+ "links": [
+ {
+ "href": "%(host)s/openstack/flavors/1",
+ "rel": "bookmark"
+ }
+ ]
+ },
+ "hostId": "%(hostid)s",
+ "id": "%(id)s",
+ "image": {
+ "id": "%(uuid)s",
+ "links": [
+ {
+ "href": "%(host)s/openstack/images/%(uuid)s",
+ "rel": "bookmark"
+ }
+ ]
+ },
+ "links": [
+ {
+ "href": "%(host)s/v2/openstack/servers/%(id)s",
+ "rel": "self"
+ },
+ {
+ "href": "%(host)s/openstack/servers/%(id)s",
+ "rel": "bookmark"
+ }
+ ],
+ "metadata": {
+ "My Server Name": "Apache1"
+ },
+ "name": "new-server-test",
+ "progress": 0,
+ "status": "ACTIVE",
+ "tenant_id": "openstack",
+ "updated": "%(timestamp)s",
+ "user_id": "fake"
+ }
+}
diff --git a/nova/tests/integrated/api_samples/OS-EXT-IPS-MAC/server-get-resp.xml.tpl b/nova/tests/integrated/api_samples/OS-EXT-IPS-MAC/server-get-resp.xml.tpl
new file mode 100644
index 000000000..532720484
--- /dev/null
+++ b/nova/tests/integrated/api_samples/OS-EXT-IPS-MAC/server-get-resp.xml.tpl
@@ -0,0 +1,19 @@
+<?xml version='1.0' encoding='UTF-8'?>
+<server xmlns:OS-EXT-IPS-MAC="http://docs.openstack.org/compute/ext/extended_ips_mac/api/v1.1" xmlns:atom="http://www.w3.org/2005/Atom" xmlns="http://docs.openstack.org/compute/api/v1.1" status="ACTIVE" updated="%(timestamp)s" hostId="%(hostid)s" name="new-server-test" created="%(timestamp)s" userId="fake" tenantId="openstack" accessIPv4="" accessIPv6="" progress="0" id="%(id)s">
+ <image id="%(uuid)s">
+ <atom:link href="%(host)s/openstack/images/%(uuid)s" rel="bookmark"/>
+ </image>
+ <flavor id="1">
+ <atom:link href="%(host)s/openstack/flavors/1" rel="bookmark"/>
+ </flavor>
+ <metadata>
+ <meta key="My Server Name">Apache1</meta>
+ </metadata>
+ <addresses>
+ <network id="private">
+ <ip version="4" addr="%(ip)s" OS-EXT-IPS-MAC:mac_addr="%(mac_addr)s"/>
+ </network>
+ </addresses>
+ <atom:link href="%(host)s/v2/openstack/servers/%(id)s" rel="self"/>
+ <atom:link href="%(host)s/openstack/servers/%(id)s" rel="bookmark"/>
+</server>
diff --git a/nova/tests/integrated/api_samples/OS-EXT-IPS-MAC/server-post-req.json.tpl b/nova/tests/integrated/api_samples/OS-EXT-IPS-MAC/server-post-req.json.tpl
new file mode 100644
index 000000000..d3916d1aa
--- /dev/null
+++ b/nova/tests/integrated/api_samples/OS-EXT-IPS-MAC/server-post-req.json.tpl
@@ -0,0 +1,16 @@
+{
+ "server" : {
+ "name" : "new-server-test",
+ "imageRef" : "%(host)s/openstack/images/%(image_id)s",
+ "flavorRef" : "%(host)s/openstack/flavors/1",
+ "metadata" : {
+ "My Server Name" : "Apache1"
+ },
+ "personality" : [
+ {
+ "path" : "/etc/banner.txt",
+ "contents" : "ICAgICAgDQoiQSBjbG91ZCBkb2VzIG5vdCBrbm93IHdoeSBpdCBtb3ZlcyBpbiBqdXN0IHN1Y2ggYSBkaXJlY3Rpb24gYW5kIGF0IHN1Y2ggYSBzcGVlZC4uLkl0IGZlZWxzIGFuIGltcHVsc2lvbi4uLnRoaXMgaXMgdGhlIHBsYWNlIHRvIGdvIG5vdy4gQnV0IHRoZSBza3kga25vd3MgdGhlIHJlYXNvbnMgYW5kIHRoZSBwYXR0ZXJucyBiZWhpbmQgYWxsIGNsb3VkcywgYW5kIHlvdSB3aWxsIGtub3csIHRvbywgd2hlbiB5b3UgbGlmdCB5b3Vyc2VsZiBoaWdoIGVub3VnaCB0byBzZWUgYmV5b25kIGhvcml6b25zLiINCg0KLVJpY2hhcmQgQmFjaA=="
+ }
+ ]
+ }
+}
diff --git a/nova/tests/integrated/api_samples/OS-EXT-IPS-MAC/server-post-req.xml.tpl b/nova/tests/integrated/api_samples/OS-EXT-IPS-MAC/server-post-req.xml.tpl
new file mode 100644
index 000000000..f92614984
--- /dev/null
+++ b/nova/tests/integrated/api_samples/OS-EXT-IPS-MAC/server-post-req.xml.tpl
@@ -0,0 +1,19 @@
+<?xml version="1.0" encoding="UTF-8"?>
+<server xmlns="http://docs.openstack.org/compute/api/v1.1" imageRef="%(host)s/openstack/images/%(image_id)s" flavorRef="%(host)s/openstack/flavors/1" name="new-server-test">
+ <metadata>
+ <meta key="My Server Name">Apache1</meta>
+ </metadata>
+ <personality>
+ <file path="/etc/banner.txt">
+ ICAgICAgDQoiQSBjbG91ZCBkb2VzIG5vdCBrbm93IHdoeSBp
+ dCBtb3ZlcyBpbiBqdXN0IHN1Y2ggYSBkaXJlY3Rpb24gYW5k
+ IGF0IHN1Y2ggYSBzcGVlZC4uLkl0IGZlZWxzIGFuIGltcHVs
+ c2lvbi4uLnRoaXMgaXMgdGhlIHBsYWNlIHRvIGdvIG5vdy4g
+ QnV0IHRoZSBza3kga25vd3MgdGhlIHJlYXNvbnMgYW5kIHRo
+ ZSBwYXR0ZXJucyBiZWhpbmQgYWxsIGNsb3VkcywgYW5kIHlv
+ dSB3aWxsIGtub3csIHRvbywgd2hlbiB5b3UgbGlmdCB5b3Vy
+ c2VsZiBoaWdoIGVub3VnaCB0byBzZWUgYmV5b25kIGhvcml6
+ b25zLiINCg0KLVJpY2hhcmQgQmFjaA==
+ </file>
+ </personality>
+</server>
diff --git a/nova/tests/integrated/api_samples/OS-EXT-IPS-MAC/server-post-resp.json.tpl b/nova/tests/integrated/api_samples/OS-EXT-IPS-MAC/server-post-resp.json.tpl
new file mode 100644
index 000000000..d5f030c87
--- /dev/null
+++ b/nova/tests/integrated/api_samples/OS-EXT-IPS-MAC/server-post-resp.json.tpl
@@ -0,0 +1,16 @@
+{
+ "server": {
+ "adminPass": "%(password)s",
+ "id": "%(id)s",
+ "links": [
+ {
+ "href": "%(host)s/v2/openstack/servers/%(uuid)s",
+ "rel": "self"
+ },
+ {
+ "href": "%(host)s/openstack/servers/%(uuid)s",
+ "rel": "bookmark"
+ }
+ ]
+ }
+}
diff --git a/nova/tests/integrated/api_samples/OS-EXT-IPS-MAC/server-post-resp.xml.tpl b/nova/tests/integrated/api_samples/OS-EXT-IPS-MAC/server-post-resp.xml.tpl
new file mode 100644
index 000000000..3bb13e69b
--- /dev/null
+++ b/nova/tests/integrated/api_samples/OS-EXT-IPS-MAC/server-post-resp.xml.tpl
@@ -0,0 +1,6 @@
+<?xml version='1.0' encoding='UTF-8'?>
+<server xmlns:atom="http://www.w3.org/2005/Atom" xmlns="http://docs.openstack.org/compute/api/v1.1" id="%(id)s" adminPass="%(password)s">
+ <metadata/>
+ <atom:link href="%(host)s/v2/openstack/servers/%(uuid)s" rel="self"/>
+ <atom:link href="%(host)s/openstack/servers/%(uuid)s" rel="bookmark"/>
+</server>
diff --git a/nova/tests/integrated/api_samples/OS-EXT-IPS-MAC/servers-detail-resp.json.tpl b/nova/tests/integrated/api_samples/OS-EXT-IPS-MAC/servers-detail-resp.json.tpl
new file mode 100644
index 000000000..6b5901098
--- /dev/null
+++ b/nova/tests/integrated/api_samples/OS-EXT-IPS-MAC/servers-detail-resp.json.tpl
@@ -0,0 +1,56 @@
+{
+ "servers": [
+ {
+ "status": "ACTIVE",
+ "updated": "%(timestamp)s",
+ "user_id": "fake",
+ "addresses": {
+ "private": [
+ {
+ "addr": "%(ip)s",
+ "version": 4,
+ "OS-EXT-IPS-MAC:mac_addr": "%(mac_addr)s"
+ }
+ ]
+ },
+ "links": [
+ {
+ "href": "%(host)s/v2/openstack/servers/%(id)s",
+ "rel": "self"
+ },
+ {
+ "href": "%(host)s/openstack/servers/%(id)s",
+ "rel": "bookmark"
+ }
+ ],
+ "created": "%(timestamp)s",
+ "name": "new-server-test",
+ "image": {
+ "id": "%(uuid)s",
+ "links": [
+ {
+ "href": "%(host)s/openstack/images/%(uuid)s",
+ "rel": "bookmark"
+ }
+ ]
+ },
+ "id": "%(uuid)s",
+ "accessIPv4": "",
+ "accessIPv6": "",
+ "tenant_id": "openstack",
+ "progress": 0,
+ "flavor": {
+ "id": "1",
+ "links": [
+ {
+ "href": "%(host)s/openstack/flavors/1",
+ "rel": "bookmark"
+ }
+ ]
+ },
+ "hostId": "%(hostid)s",
+ "metadata": {
+ "My Server Name": "Apache1"
+ }
+ }]
+}
diff --git a/nova/tests/integrated/api_samples/OS-EXT-IPS-MAC/servers-detail-resp.xml.tpl b/nova/tests/integrated/api_samples/OS-EXT-IPS-MAC/servers-detail-resp.xml.tpl
new file mode 100644
index 000000000..30902d417
--- /dev/null
+++ b/nova/tests/integrated/api_samples/OS-EXT-IPS-MAC/servers-detail-resp.xml.tpl
@@ -0,0 +1,21 @@
+<?xml version='1.0' encoding='UTF-8'?>
+<servers xmlns:OS-EXT-IPS-MAC="http://docs.openstack.org/compute/ext/extended_ips_mac/api/v1.1" xmlns:atom="http://www.w3.org/2005/Atom" xmlns="http://docs.openstack.org/compute/api/v1.1">
+ <server xmlns:OS-EXT-IPS-MAC="http://docs.openstack.org/compute/ext/extended_ips_mac/api/v1.1" xmlns:atom="http://www.w3.org/2005/Atom" xmlns="http://docs.openstack.org/compute/api/v1.1" status="ACTIVE" updated="%(timestamp)s" hostId="%(hostid)s" name="new-server-test" created="%(timestamp)s" userId="fake" tenantId="openstack" accessIPv4="" accessIPv6="" progress="0" id="%(id)s">
+ <image id="%(uuid)s">
+ <atom:link href="%(host)s/openstack/images/%(uuid)s" rel="bookmark"/>
+ </image>
+ <flavor id="1">
+ <atom:link href="%(host)s/openstack/flavors/1" rel="bookmark"/>
+ </flavor>
+ <metadata>
+ <meta key="My Server Name">Apache1</meta>
+ </metadata>
+ <addresses>
+ <network id="private">
+ <ip version="4" addr="%(ip)s" OS-EXT-IPS-MAC:mac_addr="%(mac_addr)s"/>
+ </network>
+ </addresses>
+ <atom:link href="%(host)s/v2/openstack/servers/%(id)s" rel="self"/>
+ <atom:link href="%(host)s/openstack/servers/%(id)s" rel="bookmark"/>
+ </server>
+</servers>
diff --git a/nova/tests/integrated/api_samples/all_extensions/extensions-get-resp.json.tpl b/nova/tests/integrated/api_samples/all_extensions/extensions-get-resp.json.tpl
index 05273245c..1d3d2ea90 100644
--- a/nova/tests/integrated/api_samples/all_extensions/extensions-get-resp.json.tpl
+++ b/nova/tests/integrated/api_samples/all_extensions/extensions-get-resp.json.tpl
@@ -33,6 +33,14 @@
"updated": "%(timestamp)s"
},
{
+ "alias": "OS-EXT-IPS-MAC",
+ "description": "%(text)s",
+ "links": [],
+ "name": "ExtendedIpsMac",
+ "namespace": "http://docs.openstack.org/compute/ext/extended_ips_mac/api/v1.1",
+ "updated": "%(timestamp)s"
+ },
+ {
"alias": "OS-EXT-IMG-SIZE",
"description": "%(text)s",
"links": [],
diff --git a/nova/tests/integrated/api_samples/all_extensions/extensions-get-resp.xml.tpl b/nova/tests/integrated/api_samples/all_extensions/extensions-get-resp.xml.tpl
index 9bb85f5bd..440996966 100644
--- a/nova/tests/integrated/api_samples/all_extensions/extensions-get-resp.xml.tpl
+++ b/nova/tests/integrated/api_samples/all_extensions/extensions-get-resp.xml.tpl
@@ -12,6 +12,9 @@
<extension alias="OS-EXT-IPS" updated="%(timestamp)s" namespace="http://docs.openstack.org/compute/ext/extended_ips/api/v1.1" name="ExtendedIps">
<description>%(text)s</description>
</extension>
+ <extension alias="OS-EXT-IPS-MAC" updated="%(timestamp)s" namespace="http://docs.openstack.org/compute/ext/extended_ips_mac/api/v1.1" name="ExtendedIpsMac">
+ <description>%(text)s</description>
+ </extension>
<extension alias="OS-EXT-IMG-SIZE" updated="%(timestamp)s" namespace="http://docs.openstack.org/compute/ext/image_size/api/v1.1" name="ImageSize">
<description>%(text)s</description>
</extension>
diff --git a/nova/tests/integrated/api_samples/all_extensions/server-get-resp.json.tpl b/nova/tests/integrated/api_samples/all_extensions/server-get-resp.json.tpl
index ccefc2dc7..22be331e4 100644
--- a/nova/tests/integrated/api_samples/all_extensions/server-get-resp.json.tpl
+++ b/nova/tests/integrated/api_samples/all_extensions/server-get-resp.json.tpl
@@ -15,7 +15,8 @@
{
"OS-EXT-IPS:type": "fixed",
"addr": "%(ip)s",
- "version": 4
+ "version": 4,
+ "OS-EXT-IPS-MAC:mac_addr": "%(mac_addr)s"
}
]
},
diff --git a/nova/tests/integrated/api_samples/all_extensions/server-get-resp.xml.tpl b/nova/tests/integrated/api_samples/all_extensions/server-get-resp.xml.tpl
index 973305854..35fe0a6c3 100644
--- a/nova/tests/integrated/api_samples/all_extensions/server-get-resp.xml.tpl
+++ b/nova/tests/integrated/api_samples/all_extensions/server-get-resp.xml.tpl
@@ -1,5 +1,5 @@
<?xml version='1.0' encoding='UTF-8'?>
-<server xmlns:OS-DCF="http://docs.openstack.org/compute/ext/disk_config/api/v1.1" xmlns:OS-EXT-AZ="http://docs.openstack.org/compute/ext/extended_availability_zone/api/v2" xmlns:OS-EXT-SRV-ATTR="http://docs.openstack.org/compute/ext/extended_status/api/v1.1" xmlns:OS-EXT-IPS="http://docs.openstack.org/compute/ext/extended_ips/api/v1.1" xmlns:OS-EXT-STS="http://docs.openstack.org/compute/ext/extended_status/api/v1.1" xmlns:atom="http://www.w3.org/2005/Atom" xmlns="http://docs.openstack.org/compute/api/v1.1" status="ACTIVE" updated="%(timestamp)s" hostId="%(hostid)s" name="new-server-test" created="%(timestamp)s" userId="fake" tenantId="openstack" accessIPv4="" accessIPv6="" progress="0" id="%(id)s" key_name="None" config_drive="" OS-EXT-SRV-ATTR:vm_state="active" OS-EXT-SRV-ATTR:task_state="None" OS-EXT-SRV-ATTR:power_state="1" OS-EXT-SRV-ATTR:instance_name="instance-00000001" OS-EXT-SRV-ATTR:host="%(compute_host)s" OS-EXT-SRV-ATTR:hypervisor_hostname="%(hypervisor_hostname)s" OS-EXT-AZ:availability_zone="nova" OS-DCF:diskConfig="AUTO">
+<server xmlns:OS-DCF="http://docs.openstack.org/compute/ext/disk_config/api/v1.1" xmlns:OS-EXT-AZ="http://docs.openstack.org/compute/ext/extended_availability_zone/api/v2" xmlns:OS-EXT-SRV-ATTR="http://docs.openstack.org/compute/ext/extended_status/api/v1.1" xmlns:OS-EXT-IPS="http://docs.openstack.org/compute/ext/extended_ips/api/v1.1" xmlns:OS-EXT-IPS-MAC="http://docs.openstack.org/compute/ext/extended_ips_mac/api/v1.1" xmlns:OS-EXT-STS="http://docs.openstack.org/compute/ext/extended_status/api/v1.1" xmlns:atom="http://www.w3.org/2005/Atom" xmlns="http://docs.openstack.org/compute/api/v1.1" status="ACTIVE" updated="%(timestamp)s" hostId="%(hostid)s" name="new-server-test" created="%(timestamp)s" userId="fake" tenantId="openstack" accessIPv4="" accessIPv6="" progress="0" id="%(id)s" key_name="None" config_drive="" OS-EXT-SRV-ATTR:vm_state="active" OS-EXT-SRV-ATTR:task_state="None" OS-EXT-SRV-ATTR:power_state="1" OS-EXT-SRV-ATTR:instance_name="instance-00000001" OS-EXT-SRV-ATTR:host="%(compute_host)s" OS-EXT-SRV-ATTR:hypervisor_hostname="%(hypervisor_hostname)s" OS-EXT-AZ:availability_zone="nova" OS-DCF:diskConfig="AUTO">
<image id="%(uuid)s">
<atom:link href="%(host)s/openstack/images/%(uuid)s" rel="bookmark"/>
</image>
@@ -11,7 +11,8 @@
</metadata>
<addresses>
<network id="private">
- <ip OS-EXT-IPS:type="fixed" version="4" addr="%(ip)s"/>
+ <ip OS-EXT-IPS:type="fixed" version="4" addr="%(ip)s"
+ OS-EXT-IPS-MAC:mac_addr="%(mac_addr)s"/>
</network>
</addresses>
<atom:link href="%(host)s/v2/openstack/servers/%(id)s" rel="self"/>
diff --git a/nova/tests/integrated/api_samples/all_extensions/servers-details-resp.json.tpl b/nova/tests/integrated/api_samples/all_extensions/servers-details-resp.json.tpl
index d50088837..649aa6f9b 100644
--- a/nova/tests/integrated/api_samples/all_extensions/servers-details-resp.json.tpl
+++ b/nova/tests/integrated/api_samples/all_extensions/servers-details-resp.json.tpl
@@ -16,7 +16,8 @@
{
"OS-EXT-IPS:type": "fixed",
"addr": "%(ip)s",
- "version": 4
+ "version": 4,
+ "OS-EXT-IPS-MAC:mac_addr": "%(mac_addr)s"
}
]
},
diff --git a/nova/tests/integrated/api_samples/all_extensions/servers-details-resp.xml.tpl b/nova/tests/integrated/api_samples/all_extensions/servers-details-resp.xml.tpl
index e2166c2ff..6ac363176 100644
--- a/nova/tests/integrated/api_samples/all_extensions/servers-details-resp.xml.tpl
+++ b/nova/tests/integrated/api_samples/all_extensions/servers-details-resp.xml.tpl
@@ -1,5 +1,5 @@
<?xml version='1.0' encoding='UTF-8'?>
-<servers xmlns:OS-DCF="http://docs.openstack.org/compute/ext/disk_config/api/v1.1" xmlns:OS-EXT-AZ="http://docs.openstack.org/compute/ext/extended_availability_zone/api/v2" xmlns:OS-EXT-SRV-ATTR="http://docs.openstack.org/compute/ext/extended_status/api/v1.1" xmlns:OS-EXT-IPS="http://docs.openstack.org/compute/ext/extended_ips/api/v1.1" xmlns:OS-EXT-STS="http://docs.openstack.org/compute/ext/extended_status/api/v1.1" xmlns:atom="http://www.w3.org/2005/Atom" xmlns="http://docs.openstack.org/compute/api/v1.1">
+<servers xmlns:OS-DCF="http://docs.openstack.org/compute/ext/disk_config/api/v1.1" xmlns:OS-EXT-AZ="http://docs.openstack.org/compute/ext/extended_availability_zone/api/v2" xmlns:OS-EXT-SRV-ATTR="http://docs.openstack.org/compute/ext/extended_status/api/v1.1" xmlns:OS-EXT-IPS="http://docs.openstack.org/compute/ext/extended_ips/api/v1.1" xmlns:OS-EXT-IPS-MAC="http://docs.openstack.org/compute/ext/extended_ips_mac/api/v1.1" xmlns:OS-EXT-STS="http://docs.openstack.org/compute/ext/extended_status/api/v1.1" xmlns:atom="http://www.w3.org/2005/Atom" xmlns="http://docs.openstack.org/compute/api/v1.1">
<server xmlns:OS-DCF="http://docs.openstack.org/compute/ext/disk_config/api/v1.1" xmlns:OS-EXT-AZ="http://docs.openstack.org/compute/ext/extended_availability_zone/api/v2" xmlns:OS-EXT-SRV-ATTR="http://docs.openstack.org/compute/ext/extended_status/api/v1.1" xmlns:OS-EXT-IPS="http://docs.openstack.org/compute/ext/extended_ips/api/v1.1" xmlns:OS-EXT-STS="http://docs.openstack.org/compute/ext/extended_status/api/v1.1" xmlns:atom="http://www.w3.org/2005/Atom" xmlns="http://docs.openstack.org/compute/api/v1.1" status="ACTIVE" updated="%(timestamp)s" hostId="%(hostid)s" name="new-server-test" created="%(timestamp)s" userId="fake" tenantId="openstack" accessIPv4="" accessIPv6="" progress="0" id="%(id)s" key_name="None" config_drive="" OS-EXT-SRV-ATTR:vm_state="active" OS-EXT-SRV-ATTR:task_state="None" OS-EXT-SRV-ATTR:power_state="1" OS-EXT-SRV-ATTR:instance_name="instance-00000001" OS-EXT-SRV-ATTR:host="%(compute_host)s" OS-EXT-SRV-ATTR:hypervisor_hostname="%(hypervisor_hostname)s" OS-EXT-AZ:availability_zone="nova" OS-DCF:diskConfig="AUTO">
<image id="%(uuid)s">
<atom:link href="%(host)s/openstack/images/%(uuid)s" rel="bookmark"/>
@@ -12,7 +12,8 @@
</metadata>
<addresses>
<network id="private">
- <ip OS-EXT-IPS:type="fixed" version="4" addr="%(ip)s"/>
+ <ip OS-EXT-IPS:type="fixed" version="4" addr="%(ip)s"
+ OS-EXT-IPS-MAC:mac_addr="%(mac_addr)s"/>
</network>
</addresses>
<atom:link href="%(host)s/v2/openstack/servers/%(id)s" rel="self"/>
diff --git a/nova/tests/integrated/test_api_samples.py b/nova/tests/integrated/test_api_samples.py
index 5a2327bc0..188f96055 100644
--- a/nova/tests/integrated/test_api_samples.py
+++ b/nova/tests/integrated/test_api_samples.py
@@ -461,6 +461,7 @@ class ServersSampleJsonTest(ServersSampleBase):
subs['hostid'] = '[a-f0-9]+'
subs['id'] = uuid
subs['hypervisor_hostname'] = r'[\w\.\-]+'
+ subs['mac_addr'] = '(?:[a-f0-9]{2}:){5}[a-f0-9]{2}'
return self._verify_response('server-get-resp', subs, response, 200)
def test_servers_list(self):
@@ -477,6 +478,7 @@ class ServersSampleJsonTest(ServersSampleBase):
subs['hostid'] = '[a-f0-9]+'
subs['id'] = uuid
subs['hypervisor_hostname'] = r'[\w\.\-]+'
+ subs['mac_addr'] = '(?:[a-f0-9]{2}:){5}[a-f0-9]{2}'
return self._verify_response('servers-details-resp', subs,
response, 200)
@@ -2331,6 +2333,38 @@ class ExtendedIpsSampleXmlTests(ExtendedIpsSampleJsonTests):
ctype = 'xml'
+class ExtendedIpsMacSampleJsonTests(ServersSampleBase):
+ extension_name = ("nova.api.openstack.compute.contrib"
+ ".extended_ips_mac.Extended_ips_mac")
+
+ def test_show(self):
+ uuid = self._post_server()
+ response = self._do_get('servers/%s' % uuid)
+ self.assertEqual(response.status, 200)
+ subs = self._get_regexes()
+ subs['hostid'] = '[a-f0-9]+'
+ subs['id'] = uuid
+ subs['hypervisor_hostname'] = r'[\w\.\-]+'
+ subs['mac_addr'] = '(?:[a-f0-9]{2}:){5}[a-f0-9]{2}'
+ return self._verify_response('server-get-resp', subs,
+ response, 200)
+
+ def test_detail(self):
+ uuid = self._post_server()
+ response = self._do_get('servers/detail')
+ self.assertEqual(response.status, 200)
+ subs = self._get_regexes()
+ subs['id'] = uuid
+ subs['hostid'] = '[a-f0-9]+'
+ subs['mac_addr'] = '(?:[a-f0-9]{2}:){5}[a-f0-9]{2}'
+ return self._verify_response('servers-detail-resp', subs,
+ response, 200)
+
+
+class ExtendedIpsMacSampleXmlTests(ExtendedIpsMacSampleJsonTests):
+ ctype = 'xml'
+
+
class ExtendedStatusSampleJsonTests(ServersSampleBase):
extension_name = ("nova.api.openstack.compute.contrib"
".extended_status.Extended_status")