diff --git a/daemon/core/api/grpc/client.py b/daemon/core/api/grpc/client.py index cb24d979..496c722f 100644 --- a/daemon/core/api/grpc/client.py +++ b/daemon/core/api/grpc/client.py @@ -880,17 +880,18 @@ class CoreGrpcClient(object): with open(file_path, "w") as xml_file: xml_file.write(response.data) - def open_xml(self, file_path): + def open_xml(self, file_path, start=False): """ Load a local scenario XML file to open as a new session. :param str file_path: path of scenario XML file + :param bool start: True to start session, False otherwise :return: response with opened session id :rtype: core_pb2.OpenXmlResponse """ with open(file_path, "r") as xml_file: data = xml_file.read() - request = core_pb2.OpenXmlRequest(data=data) + request = core_pb2.OpenXmlRequest(data=data, start=start, file=file_path) return self.stub.OpenXml(request) def emane_link(self, session_id, nem_one, nem_two, linked): diff --git a/daemon/core/api/grpc/server.py b/daemon/core/api/grpc/server.py index 85838827..de73dca1 100644 --- a/daemon/core/api/grpc/server.py +++ b/daemon/core/api/grpc/server.py @@ -305,7 +305,10 @@ class CoreGrpcServer(core_pb2_grpc.CoreApiServicer): for session_id in self.coreemu.sessions: session = self.coreemu.sessions[session_id] session_summary = core_pb2.SessionSummary( - id=session_id, state=session.state, nodes=session.get_node_count() + id=session_id, + state=session.state, + nodes=session.get_node_count(), + file=session.file_name, ) sessions.append(session_summary) return core_pb2.GetSessionsResponse(sessions=sessions) @@ -1555,19 +1558,22 @@ class CoreGrpcServer(core_pb2_grpc.CoreApiServicer): """ logging.debug("open xml: %s", request) session = self.coreemu.create_session() - session.set_state(EventTypes.CONFIGURATION_STATE) - _, temp_path = tempfile.mkstemp() - with open(temp_path, "w") as xml_file: - xml_file.write(request.data) + temp = tempfile.NamedTemporaryFile(delete=False) + temp.write(request.data.encode("utf-8")) + temp.close() try: - session.open_xml(temp_path, start=True) + session.open_xml(temp.name, request.start) + session.name = os.path.basename(request.file) + session.file_name = request.file return core_pb2.OpenXmlResponse(session_id=session.id, result=True) except IOError: logging.exception("error opening session file") self.coreemu.delete_session(session.id) context.abort(grpc.StatusCode.INVALID_ARGUMENT, "invalid xml file") + finally: + os.unlink(temp.name) def GetInterfaces(self, request, context): """ diff --git a/daemon/core/api/tlv/corehandlers.py b/daemon/core/api/tlv/corehandlers.py index 41bac314..1e15377a 100644 --- a/daemon/core/api/tlv/corehandlers.py +++ b/daemon/core/api/tlv/corehandlers.py @@ -944,7 +944,7 @@ class CoreHandler(socketserver.BaseRequestHandler): if os.path.splitext(file_name)[1].lower() == ".xml": session = self.coreemu.create_session(master=False) try: - session.open_xml(file_name, start=True) + session.open_xml(file_name) except Exception: self.coreemu.delete_session(session.id) raise diff --git a/daemon/core/emulator/session.py b/daemon/core/emulator/session.py index 179c580d..ee0c5d1f 100644 --- a/daemon/core/emulator/session.py +++ b/daemon/core/emulator/session.py @@ -820,19 +820,24 @@ class Session(object): :param bool start: instantiate session if true, false otherwise :return: nothing """ + logging.info("opening xml: %s", file_name) + # clear out existing session self.clear() if start: - self.set_state(EventTypes.CONFIGURATION_STATE) + state = EventTypes.CONFIGURATION_STATE + else: + state = EventTypes.DEFINITION_STATE + self.set_state(state) + self.name = os.path.basename(file_name) + self.file_name = file_name # write out xml file CoreXmlReader(self).read(file_name) # start session if needed if start: - self.name = os.path.basename(file_name) - self.file_name = file_name self.instantiate() def save_xml(self, file_name): diff --git a/daemon/core/xml/corexml.py b/daemon/core/xml/corexml.py index f4a360c6..220175bc 100644 --- a/daemon/core/xml/corexml.py +++ b/daemon/core/xml/corexml.py @@ -304,10 +304,8 @@ class CoreXmlWriter(object): default_options = self.session.options.default_values() for _id in default_options: default_value = default_options[_id] - # TODO: should we just save the current config regardless, since it may change? - value = options_config[_id] - if value != default_value: - add_configuration(option_elements, _id, value) + value = options_config.get(_id, default_value) + add_configuration(option_elements, _id, value) if option_elements.getchildren(): self.scenario.append(option_elements) diff --git a/daemon/proto/core/api/grpc/core.proto b/daemon/proto/core/api/grpc/core.proto index db43dec6..af1768ce 100644 --- a/daemon/proto/core/api/grpc/core.proto +++ b/daemon/proto/core/api/grpc/core.proto @@ -631,6 +631,8 @@ message SaveXmlResponse { message OpenXmlRequest { string data = 1; + bool start = 2; + string file = 3; } message OpenXmlResponse { @@ -798,6 +800,7 @@ message SessionSummary { int32 id = 1; SessionState.Enum state = 2; int32 nodes = 3; + string file = 4; } message Node {