Default host binding is 0.0.0.0.

Move the file uploader template.
UDP port allocation (removed the host).
Minor changes with iouyap lookup and remote server project directory.
pull/11/head
grossmj 10 years ago
parent f534a02324
commit c91f876656

@ -21,6 +21,7 @@ Simple file upload & listing handler.
import os import os
import stat
import tornado.web import tornado.web
from ..config import Config from ..config import Config
@ -74,4 +75,6 @@ class FileUploadHandler(tornado.web.RequestHandler):
destination_path = os.path.join(self._upload_dir, fileinfo['filename']) destination_path = os.path.join(self._upload_dir, fileinfo['filename'])
with open(destination_path, 'wb') as f: with open(destination_path, 'wb') as f:
f.write(fileinfo['body']) f.write(fileinfo['body'])
st = os.stat(destination_path)
os.chmod(destination_path, st.st_mode | stat.S_IXUSR)
self.redirect("/upload") self.redirect("/upload")

@ -110,10 +110,11 @@ class Dynamips(IModule):
self._frame_relay_switches = {} self._frame_relay_switches = {}
self._atm_switches = {} self._atm_switches = {}
self._ethernet_hubs = {} self._ethernet_hubs = {}
self._projects_dir = kwargs["projects_dir"] self._projects_dir = os.path.join(kwargs["projects_dir"], "dynamips")
self._tempdir = kwargs["temp_dir"] self._tempdir = kwargs["temp_dir"]
self._working_dir = self._projects_dir self._working_dir = self._projects_dir
self._dynamips = "" self._dynamips = ""
self._default_host = "0.0.0.0"
self._callback = self.add_periodic_callback(self._check_hypervisors, 5000) self._callback = self.add_periodic_callback(self._check_hypervisors, 5000)
self._callback.start() self._callback.start()
@ -199,16 +200,18 @@ class Dynamips(IModule):
if not os.access(self._dynamips, os.X_OK): if not os.access(self._dynamips, os.X_OK):
raise DynamipsError("Dynamips {} is not executable".format(self._dynamips)) raise DynamipsError("Dynamips {} is not executable".format(self._dynamips))
# check if the working directory exists
if not os.path.exists(self._working_dir): if not os.path.exists(self._working_dir):
raise DynamipsError("Working directory {} doesn't exist".format(self._working_dir)) try:
os.makedirs(self._working_dir)
except EnvironmentError as e:
raise DynamipsError("Could not create working directory {}".format(e))
# check if the working directory is writable # check if the working directory is writable
if not os.access(self._working_dir, os.W_OK): if not os.access(self._working_dir, os.W_OK):
raise DynamipsError("Cannot write to working directory {}".format(self._working_dir)) raise DynamipsError("Cannot write to working directory {}".format(self._working_dir))
log.info("starting the hypervisor manager with Dynamips working directory set to '{}'".format(self._working_dir)) log.info("starting the hypervisor manager with Dynamips working directory set to '{}'".format(self._working_dir))
self._hypervisor_manager = HypervisorManager(self._dynamips, self._working_dir) self._hypervisor_manager = HypervisorManager(self._dynamips, self._working_dir, self._default_host)
for name, value in self._hypervisor_manager_settings.items(): for name, value in self._hypervisor_manager_settings.items():
if hasattr(self._hypervisor_manager, name) and getattr(self._hypervisor_manager, name) != value: if hasattr(self._hypervisor_manager, name) and getattr(self._hypervisor_manager, name) != value:
@ -245,7 +248,8 @@ class Dynamips(IModule):
else: else:
self._remote_server = True self._remote_server = True
log.info("this server is remote") log.info("this server is remote")
self._working_dir = self._projects_dir self._working_dir = os.path.join(self._projects_dir, request["project_name"])
log.info("this server is remote with working directory path to {}".format(self._working_dir))
self._hypervisor_manager_settings = request self._hypervisor_manager_settings = request
@ -329,8 +333,7 @@ class Dynamips(IModule):
node.id, node.id,
port, port,
host)) host))
response = {"lport": port, response = {"lport": port}
"lhost": host}
return response return response
@ -421,5 +424,8 @@ class Dynamips(IModule):
:param request: JSON request :param request: JSON request
""" """
import netifaces try:
import netifaces
except ImportError:
raise DynamipsError("The netifaces module is not installed")
self.send_response(netifaces.interfaces()) self.send_response(netifaces.interfaces())

@ -141,7 +141,6 @@ class ATMSW(object):
Response parameters: Response parameters:
- port_id (port identifier) - port_id (port identifier)
- lhost (local host address)
- lport (allocated local port) - lport (allocated local port)
:param request: JSON request :param request: JSON request

@ -140,7 +140,6 @@ class ETHHUB(object):
Response parameters: Response parameters:
- port_id (port identifier) - port_id (port identifier)
- lhost (local host address)
- lport (allocated local port) - lport (allocated local port)
:param request: JSON request :param request: JSON request

@ -159,7 +159,6 @@ class ETHSW(object):
Response parameters: Response parameters:
- port_id (port identifier) - port_id (port identifier)
- lhost (local host address)
- lport (allocated local port) - lport (allocated local port)
:param request: JSON request :param request: JSON request

@ -139,7 +139,6 @@ class FRSW(object):
Response parameters: Response parameters:
- port_id (port identifier) - port_id (port identifier)
- lhost (local host address)
- lport (allocated local port) - lport (allocated local port)
:param request: JSON request :param request: JSON request

@ -537,7 +537,6 @@ class VM(object):
Response parameters: Response parameters:
- port_id (unique port identifier) - port_id (unique port identifier)
- lhost (local host address)
- lport (allocated local port) - lport (allocated local port)
:param request: JSON request :param request: JSON request

@ -273,5 +273,5 @@ class Hypervisor(DynamipsHypervisor):
if self._host != '0.0.0.0': if self._host != '0.0.0.0':
command.extend(['-H', self._host + ':' + str(self._port)]) command.extend(['-H', self._host + ':' + str(self._port)])
else: else:
command.extend(['-H', self._port]) command.extend(['-H', str(self._port)])
return command return command

@ -54,13 +54,18 @@ class IOU(IModule):
config = Config.instance() config = Config.instance()
iou_config = config.get_section_config(name.upper()) iou_config = config.get_section_config(name.upper())
self._iouyap = iou_config.get("iouyap") self._iouyap = iou_config.get("iouyap")
if not self._iouyap:
for path in os.environ["PATH"].split(":"):
if "iouyap" in os.listdir(path) and os.access("iouyap", os.X_OK):
self._iouyap = os.path.join(path, "iouyap")
break
if not self._iouyap or not os.path.exists(self._iouyap): if not self._iouyap or not os.path.exists(self._iouyap):
iouyap_in_cwd = os.path.join(os.getcwd(), "iouyap")
if os.path.exists(iouyap_in_cwd):
self._iouyap = iouyap_in_cwd
else:
# look for iouyap if none is defined or accessible
for path in os.environ["PATH"].split(":"):
if "iouyap" in os.listdir(path) and os.access(os.path.join(path, "iouyap"), os.X_OK):
self._iouyap = os.path.join(path, "iouyap")
break
if not self._iouyap:
log.warning("iouyap binary couldn't be found!") log.warning("iouyap binary couldn't be found!")
elif not os.access(self._iouyap, os.X_OK): elif not os.access(self._iouyap, os.X_OK):
log.warning("iouyap is not executable") log.warning("iouyap is not executable")
@ -75,8 +80,8 @@ class IOU(IModule):
self._udp_start_port_range = 30001 self._udp_start_port_range = 30001
self._udp_end_port_range = 40001 self._udp_end_port_range = 40001
self._current_udp_port = self._udp_start_port_range self._current_udp_port = self._udp_start_port_range
self._host = "127.0.0.1" # FIXME: used by ZeroMQ... self._default_host = "0.0.0.0"
self._projects_dir = kwargs["projects_dir"] self._projects_dir = os.path.join(kwargs["projects_dir"], "iou")
self._tempdir = kwargs["temp_dir"] self._tempdir = kwargs["temp_dir"]
self._working_dir = self._projects_dir self._working_dir = self._projects_dir
self._iourc = "" self._iourc = ""
@ -146,6 +151,7 @@ class IOU(IModule):
if self._iourc and os.path.exists(self._iourc): if self._iourc and os.path.exists(self._iourc):
try: try:
log.info("deleting iourc file {}".format(self._iourc))
os.remove(self._iourc) os.remove(self._iourc)
except EnvironmentError as e: except EnvironmentError as e:
log.warn("could not delete iourc file {}: {}".format(self._iourc, e)) log.warn("could not delete iourc file {}: {}".format(self._iourc, e))
@ -162,6 +168,7 @@ class IOU(IModule):
Optional request parameters: Optional request parameters:
- working_dir (path to a working directory) - working_dir (path to a working directory)
- project_name
- console_start_port_range - console_start_port_range
- console_end_port_range - console_end_port_range
- udp_start_port_range - udp_start_port_range
@ -196,8 +203,8 @@ class IOU(IModule):
iou_instance.working_dir = self._working_dir iou_instance.working_dir = self._working_dir
else: else:
self._remote_server = True self._remote_server = True
log.info("this server is remote") self._working_dir = os.path.join(self._projects_dir, request["project_name"])
self._working_dir = self._projects_dir log.info("this server is remote with working directory path to {}".format(self._working_dir))
if "console_start_port_range" in request and "console_end_port_range" in request: if "console_start_port_range" in request and "console_end_port_range" in request:
self._console_start_port_range = request["console_start_port_range"] self._console_start_port_range = request["console_start_port_range"]
@ -233,11 +240,17 @@ class IOU(IModule):
iou_path = request["path"] iou_path = request["path"]
try: try:
iou_instance = IOUDevice(iou_path, self._working_dir, name=name) if not os.path.exists(self._working_dir):
try:
os.makedirs(self._working_dir)
except EnvironmentError as e:
raise IOUError("Could not create working directory {}".format(e))
iou_instance = IOUDevice(iou_path, self._working_dir, host=self._default_host, name=name)
# find a console port # find a console port
if self._current_console_port >= self._console_end_port_range: if self._current_console_port >= self._console_end_port_range:
self._current_console_port = self._console_start_port_range self._current_console_port = self._console_start_port_range
iou_instance.console = IOUDevice.find_unused_port(self._current_console_port, self._console_end_port_range, self._host) iou_instance.console = IOUDevice.find_unused_port(self._current_console_port, self._console_end_port_range, self._default_host)
self._current_console_port += 1 self._current_console_port += 1
except IOUError as e: except IOUError as e:
self.send_custom_error(str(e)) self.send_custom_error(str(e))
@ -441,7 +454,6 @@ class IOU(IModule):
Response parameters: Response parameters:
- port_id (unique port identifier) - port_id (unique port identifier)
- lhost (local host address)
- lport (allocated local port) - lport (allocated local port)
:param request: JSON request :param request: JSON request
@ -461,15 +473,14 @@ class IOU(IModule):
# find a UDP port # find a UDP port
if self._current_udp_port >= self._udp_end_port_range: if self._current_udp_port >= self._udp_end_port_range:
self._current_udp_port = self._udp_start_port_range self._current_udp_port = self._udp_start_port_range
port = IOUDevice.find_unused_port(self._current_udp_port, self._udp_end_port_range, host=self._host, socket_type="UDP") port = IOUDevice.find_unused_port(self._current_udp_port, self._udp_end_port_range, host=self._default_host, socket_type="UDP")
self._current_udp_port += 1 self._current_udp_port += 1
log.info("{} [id={}] has allocated UDP port {} with host {}".format(iou_instance .name, log.info("{} [id={}] has allocated UDP port {} with host {}".format(iou_instance .name,
iou_instance .id, iou_instance .id,
port, port,
self._host)) self._default_host))
response = {"lport": port, response = {"lport": port}
"lhost": self._host}
except IOUError as e: except IOUError as e:
self.send_custom_error(str(e)) self.send_custom_error(str(e))

@ -37,7 +37,6 @@ from .config import Config
from .handlers.jsonrpc_websocket import JSONRPCWebSocket from .handlers.jsonrpc_websocket import JSONRPCWebSocket
from .handlers.version_handler import VersionHandler from .handlers.version_handler import VersionHandler
from .handlers.file_upload_handler import FileUploadHandler from .handlers.file_upload_handler import FileUploadHandler
from .module_manager import ModuleManager
from .modules import MODULES from .modules import MODULES
import logging import logging
@ -129,9 +128,11 @@ class Server(object):
router = self._create_zmq_router() router = self._create_zmq_router()
# Add our JSON-RPC Websocket handler to Tornado # Add our JSON-RPC Websocket handler to Tornado
self.handlers.extend([(r"/", JSONRPCWebSocket, dict(zmq_router=router))]) self.handlers.extend([(r"/", JSONRPCWebSocket, dict(zmq_router=router))])
tornado_app = tornado.web.Application(self.handlers, debug=True) # FIXME: debug mode! tornado_app = tornado.web.Application(self.handlers,
template_path=os.path.join(os.path.dirname(__file__), "templates"),
debug=True) # FIXME: debug mode!
try: try:
print("Starting server on port {}".format(self._port)) print("Starting server on {}:{}".format(self._host, self._port))
tornado_app.listen(self._port, address=self._host) tornado_app.listen(self._port, address=self._host)
except socket.error as e: except socket.error as e:
if e.errno == errno.EADDRINUSE: # socket already in use if e.errno == errno.EADDRINUSE: # socket already in use

@ -15,7 +15,7 @@ File: <input type="file" name="file" />
<h3>Files</h3> <h3>Files</h3>
<ul> <ul>
{%for item in items%} {%for item in items%}
<li>{{path}}{{item}}</a></li> <li>{{path}}/{{item}}</a></li>
{%end%} {%end%}
{%end%} {%end%}
</ul> </ul>

@ -42,7 +42,7 @@ setup(
cmdclass={"test": Tox}, cmdclass={"test": Tox},
author="Jeremy Grossmann", author="Jeremy Grossmann",
author_email="package-maintainer@gns3.net", author_email="package-maintainer@gns3.net",
description="GNS3 server to asynchronously to manage emulators", description="GNS3 server to asynchronously manage emulators",
long_description=open("README.rst", "r").read(), long_description=open("README.rst", "r").read(),
install_requires=[ install_requires=[
"tornado >= 2.0", "tornado >= 2.0",
@ -54,6 +54,7 @@ setup(
] ]
}, },
packages=find_packages(), packages=find_packages(),
package_data={"gns3server": ["templates/upload.html"]},
include_package_data=True, include_package_data=True,
platforms="any", platforms="any",
classifiers=[ classifiers=[

Loading…
Cancel
Save