Merged trunk.

This commit is contained in:
Brian Lamar
2011-03-30 09:38:09 -04:00
8 changed files with 173 additions and 12 deletions

View File

@@ -14,3 +14,8 @@ CA/newcerts/*.pem
CA/private/cakey.pem
nova/vcsversion.py
*.DS_Store
.project
.pydevproject
clean.sqlite
run_tests.log
tests.sqlite

View File

@@ -12,6 +12,7 @@ Chiradeep Vittal <chiradeep@cloud.com>
Chmouel Boudjnah <chmouel@chmouel.com>
Chris Behrens <cbehrens@codestud.com>
Christian Berendt <berendt@b1-systems.de>
Chuck Short <zulcss@ubuntu.com>
Cory Wright <corywright@gmail.com>
Dan Prince <dan.prince@rackspace.com>
David Pravec <David.Pravec@danix.org>

View File

@@ -108,17 +108,17 @@ class AjaxConsoleProxy(object):
return "Server Error"
def register_listeners(self):
class Callback:
def __call__(self, data, message):
if data['method'] == 'authorize_ajax_console':
AjaxConsoleProxy.tokens[data['args']['token']] = \
{'args': data['args'], 'last_activity': time.time()}
class TopicProxy():
@staticmethod
def authorize_ajax_console(context, **kwargs):
AjaxConsoleProxy.tokens[kwargs['token']] = \
{'args': kwargs, 'last_activity': time.time()}
conn = rpc.Connection.instance(new=True)
consumer = rpc.TopicAdapterConsumer(
connection=conn,
topic=FLAGS.ajax_console_proxy_topic)
consumer.register_callback(Callback())
connection=conn,
proxy=TopicProxy,
topic=FLAGS.ajax_console_proxy_topic)
def delete_expired_tokens():
now = time.time()
@@ -130,8 +130,7 @@ class AjaxConsoleProxy(object):
for k in to_delete:
del AjaxConsoleProxy.tokens[k]
utils.LoopingCall(consumer.fetch, auto_ack=True,
enable_callbacks=True).start(0.1)
utils.LoopingCall(consumer.fetch, enable_callbacks=True).start(0.1)
utils.LoopingCall(delete_expired_tokens).start(1)
if __name__ == '__main__':

View File

@@ -48,6 +48,7 @@ flags.DECLARE('auth_driver', 'nova.auth.manager')
flags.DECLARE('network_size', 'nova.network.manager')
flags.DECLARE('num_networks', 'nova.network.manager')
flags.DECLARE('update_dhcp_on_disassociate', 'nova.network.manager')
flags.DEFINE_string('dnsmasq_interface', 'br0', 'Default Dnsmasq interface')
LOG = logging.getLogger('nova.dhcpbridge')
@@ -103,7 +104,8 @@ def main():
utils.default_flagfile(flagfile)
argv = FLAGS(sys.argv)
logging.setup()
interface = os.environ.get('DNSMASQ_INTERFACE', 'br0')
# check ENV first so we don't break any older deploys
interface = os.environ.get('DNSMASQ_INTERFACE', FLAGS.dnsmasq_interface)
if int(os.environ.get('TESTING', '0')):
from nova.tests import fake_flags
action = argv[1]

View File

@@ -1125,7 +1125,7 @@ def main():
print _("Possible wrong number of arguments supplied")
print "%s %s: %s" % (category, action, fn.__doc__)
raise
except:
except Exception:
print _("Command failed, please check log for more info")
raise

101
bin/nova-vncproxy Executable file
View File

@@ -0,0 +1,101 @@
#!/usr/bin/env python
# vim: tabstop=4 shiftwidth=4 softtabstop=4
# Copyright (c) 2010 Openstack, LLC.
# 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.
"""VNC Console Proxy Server."""
import eventlet
import gettext
import os
import sys
possible_topdir = os.path.normpath(os.path.join(os.path.abspath(sys.argv[0]),
os.pardir,
os.pardir))
if os.path.exists(os.path.join(possible_topdir, 'nova', '__init__.py')):
sys.path.insert(0, possible_topdir)
gettext.install('nova', unicode=1)
from nova import flags
from nova import log as logging
from nova import service
from nova import utils
from nova import wsgi
from nova import version
from nova.vnc import auth
from nova.vnc import proxy
LOG = logging.getLogger('nova.vnc-proxy')
FLAGS = flags.FLAGS
flags.DEFINE_string('vncproxy_wwwroot', '/var/lib/nova/noVNC/',
'Full path to noVNC directory')
flags.DEFINE_boolean('vnc_debug', False,
'Enable debugging features, like token bypassing')
flags.DEFINE_integer('vncproxy_port', 6080,
'Port that the VNC proxy should bind to')
flags.DEFINE_string('vncproxy_host', '0.0.0.0',
'Address that the VNC proxy should bind to')
flags.DEFINE_integer('vnc_token_ttl', 300,
'How many seconds before deleting tokens')
flags.DEFINE_string('vncproxy_manager', 'nova.vnc.auth.VNCProxyAuthManager',
'Manager for vncproxy auth')
flags.DEFINE_flag(flags.HelpFlag())
flags.DEFINE_flag(flags.HelpshortFlag())
flags.DEFINE_flag(flags.HelpXMLFlag())
if __name__ == "__main__":
utils.default_flagfile()
FLAGS(sys.argv)
logging.setup()
LOG.audit(_("Starting nova-vnc-proxy node (version %s)"),
version.version_string_with_vcs())
if not (os.path.exists(FLAGS.vncproxy_wwwroot) and
os.path.exists(FLAGS.vncproxy_wwwroot + '/vnc_auto.html')):
LOG.info(_("Missing vncproxy_wwwroot (version %s)"),
FLAGS.vncproxy_wwwroot)
LOG.info(_("You need a slightly modified version of noVNC "
"to work with the nova-vnc-proxy"))
LOG.info(_("Check out the most recent nova noVNC code: %s"),
"git://github.com/sleepsonthefloor/noVNC.git")
LOG.info(_("And drop it in %s"), FLAGS.vncproxy_wwwroot)
exit(1)
app = proxy.WebsocketVNCProxy(FLAGS.vncproxy_wwwroot)
LOG.audit(_("Allowing access to the following files: %s"),
app.get_whitelist())
with_logging = auth.LoggingMiddleware(app)
if FLAGS.vnc_debug:
with_auth = proxy.DebugMiddleware(with_logging)
else:
with_auth = auth.VNCNovaAuthMiddleware(with_logging)
service.serve()
server = wsgi.Server()
server.start(with_auth, FLAGS.vncproxy_port, host=FLAGS.vncproxy_host)
server.wait()

View File

@@ -286,6 +286,16 @@ class ComputeTestCase(test.TestCase):
console = self.compute.get_ajax_console(self.context,
instance_id)
self.assert_(set(['token', 'host', 'port']).issubset(console.keys()))
self.compute.terminate_instance(self.context, instance_id)
def test_vnc_console(self):
"""Make sure we can a vnc console for an instance."""
instance_id = self._create_instance()
self.compute.run_instance(self.context, instance_id)
console = self.compute.get_vnc_console(self.context,
instance_id)
self.assert_(console)
self.compute.terminate_instance(self.context, instance_id)

View File

@@ -225,6 +225,49 @@ class LibvirtConnTestCase(test.TestCase):
self._check_xml_and_uri(instance_data, expect_kernel=True,
expect_ramdisk=True, rescue=True)
def test_lxc_container_and_uri(self):
instance_data = dict(self.test_instance)
self._check_xml_and_container(instance_data)
def _check_xml_and_container(self, instance):
user_context = context.RequestContext(project=self.project,
user=self.user)
instance_ref = db.instance_create(user_context, instance)
host = self.network.get_network_host(user_context.elevated())
network_ref = db.project_get_network(context.get_admin_context(),
self.project.id)
fixed_ip = {'address': self.test_ip,
'network_id': network_ref['id']}
ctxt = context.get_admin_context()
fixed_ip_ref = db.fixed_ip_create(ctxt, fixed_ip)
db.fixed_ip_update(ctxt, self.test_ip,
{'allocated': True,
'instance_id': instance_ref['id']})
self.flags(libvirt_type='lxc')
conn = libvirt_conn.LibvirtConnection(True)
uri = conn.get_uri()
self.assertEquals(uri, 'lxc:///')
xml = conn.to_xml(instance_ref)
tree = xml_to_tree(xml)
check = [
(lambda t: t.find('.').get('type'), 'lxc'),
(lambda t: t.find('./os/type').text, 'exe'),
(lambda t: t.find('./devices/filesystem/target').get('dir'), '/')]
for i, (check, expected_result) in enumerate(check):
self.assertEqual(check(tree),
expected_result,
'%s failed common check %d' % (xml, i))
target = tree.find('./devices/filesystem/source').get('dir')
self.assertTrue(len(target) > 0)
def _check_xml_and_uri(self, instance, expect_ramdisk, expect_kernel,
rescue=False):
user_context = context.RequestContext(project=self.project,