3 # Copyright (C) 2007, 2008 Google Inc.
5 # This program is free software; you can redistribute it and/or modify
6 # it under the terms of the GNU General Public License as published by
7 # the Free Software Foundation; either version 2 of the License, or
8 # (at your option) any later version.
10 # This program is distributed in the hope that it will be useful, but
11 # WITHOUT ANY WARRANTY; without even the implied warranty of
12 # MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
13 # General Public License for more details.
15 # You should have received a copy of the GNU General Public License
16 # along with this program; if not, write to the Free Software
17 # Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
21 """Remote API QA tests.
27 from ganeti import utils
28 from ganeti import constants
29 from ganeti import errors
30 from ganeti import serializer
36 from qa_utils import AssertEqual, AssertNotEqual, AssertIn, StartSSH
39 # Create opener which doesn't try to look for proxies.
40 NoProxyOpener = urllib2.build_opener(urllib2.ProxyHandler({}))
43 INSTANCE_FIELDS = ("name", "os", "pnode", "snodes",
44 "admin_state", "admin_ram",
45 "disk_template", "ip", "mac", "bridge",
46 "sda_size", "sdb_size", "vcpus",
47 "oper_state", "status", "tags")
49 NODE_FIELDS = ("name", "dtotal", "dfree",
50 "mtotal", "mnode", "mfree",
51 "pinst_cnt", "sinst_cnt", "tags")
53 LIST_FIELDS = ("name", "uri")
57 """Return whether remote API tests should be run.
60 return constants.RAPI_ENABLE and qa_config.TestEnabled('rapi')
63 def PrintRemoteAPIWarning():
64 """Print warning if remote API is not enabled.
67 if constants.RAPI_ENABLE or not qa_config.TestEnabled('rapi'):
69 msg = ("Remote API is not enabled in this Ganeti build. Please run"
70 " `configure [...] --enable-rapi'.")
72 print qa_utils.FormatWarning(msg)
76 master = qa_config.GetMasterNode()
77 host = master["primary"]
78 port = qa_config.get("rapi-port", default=constants.RAPI_PORT)
80 for uri, verify in uris:
81 assert uri.startswith("/")
83 url = "http://%s:%s%s" % (host, port, uri)
85 print "Testing %s ..." % url
87 response = NoProxyOpener.open(url)
89 AssertEqual(response.info()["Content-type"], "application/json")
91 data = serializer.LoadJson(response.read())
93 if verify is not None:
97 AssertEqual(data, verify)
100 @qa_utils.DefineHook('rapi-version')
102 """Testing remote API version.
106 ("/version", constants.RAPI_VERSION),
110 @qa_utils.DefineHook('rapi-empty-cluster')
111 def TestEmptyCluster():
112 """Testing remote API on an empty cluster.
115 master_name = qa_config.GetMasterNode()["primary"]
117 def _VerifyInfo(data):
118 AssertIn("name", data)
119 AssertIn("master", data)
120 AssertEqual(data["master"], master_name)
122 def _VerifyNodes(data):
125 "uri": "/nodes/%s" % master_name,
127 AssertIn(master_entry, data)
129 def _VerifyNodesBulk(data):
131 for entry in NODE_FIELDS:
132 AssertIn(entry, node)
136 ("/info", _VerifyInfo),
138 ("/nodes", _VerifyNodes),
139 ("/nodes?bulk=1", _VerifyNodesBulk),
141 ("/instances?bulk=1", []),
146 @qa_utils.DefineHook('rapi-instance')
147 def TestInstance(instance):
148 """Testing getting instance(s) info via remote API.
151 def _VerifyInstance(data):
152 for entry in INSTANCE_FIELDS:
153 AssertIn(entry, data)
155 def _VerifyInstancesList(data):
156 for instance in data:
157 for entry in LIST_FIELDS:
158 AssertIn(entry, instance)
160 def _VerifyInstancesBulk(data):
161 for instance_data in data:
162 _VerifyInstance(instance_data)
165 ("/instances/%s" % instance["name"], _VerifyInstance),
166 ("/instances", _VerifyInstancesList),
167 ("/instances?bulk=1", _VerifyInstancesBulk),
171 @qa_utils.DefineHook('rapi-node')
173 """Testing getting node(s) info via remote API.
176 def _VerifyNode(data):
177 for entry in NODE_FIELDS:
178 AssertIn(entry, data)
180 def _VerifyNodesList(data):
182 for entry in LIST_FIELDS:
183 AssertIn(entry, node)
185 def _VerifyNodesBulk(data):
186 for node_data in data:
187 _VerifyNode(node_data)
190 ("/nodes/%s" % node["primary"], _VerifyNode),
191 ("/nodes", _VerifyNodesList),
192 ("/nodes?bulk=1", _VerifyNodesBulk),
196 def TestTags(kind, name, tags):
197 """Tests .../tags resources.
200 if kind == constants.TAG_CLUSTER:
202 elif kind == constants.TAG_NODE:
203 uri = "/nodes/%s/tags" % name
204 elif kind == constants.TAG_INSTANCE:
205 uri = "/instances/%s/tags" % name
207 raise errors.ProgrammerError("Unknown tag kind")
209 def _VerifyTags(data):
210 # Create copies to modify
216 AssertEqual(should, returned)