indexing description: "Represents a rendezvous propagate message element" license: "MIT license (see ../../license.txt)" author: "Beat Strasser " date: "$Date$" revision: "$Revision$" class P2P_RENDEZVOUS_PROPAGATE inherit P2P_XML_CACHE redefine initialize, document, validate end P2P_UUID_TOOLS export {NONE} all undefine out end create make, parse_from_string, make_from_element feature {NONE} -- Initialization make (a_destination_service_name: like destination_service_name; a_destination_service_parameter: like destination_service_parameter; a_ttl: like ttl; a_path: STRING) is -- Create new rendezvous propagate message element with a new, random `message_id' require Service_name_valid: a_destination_service_name /= Void Ttl_valid: a_ttl >= 0 Path_valid: a_path /= Void do initialize create_random_uuid (message_id, 0) set_destination_service_name (a_destination_service_name) if a_destination_service_parameter /= Void then set_destination_service_parameter (a_destination_service_parameter) end set_ttl (a_ttl) add_path (a_path) is_valid := True end feature -- Access message_id: ARRAY [NATURAL_8] destination_service_name: STRING destination_service_parameter: STRING ttl: INTEGER paths: DS_LIST [STRING] has_path (a_path: STRING): BOOLEAN is -- Is `a_path' available in message? do from paths.start until Result or paths.after loop Result := paths.item_for_iteration.is_equal (a_path) paths.forth end end match (an_element_name, an_element_value: STRING): BOOLEAN is -- Is given element's value equal with `an_element_value'? do if element_message_id.is_equal (an_element_name) then Result := does_element_match (uuid_string (message_id, 0), an_element_value) elseif element_destination_service_name.is_equal (an_element_name) then Result := does_element_match (destination_service_name, an_element_value) elseif element_destination_service_parameter.is_equal (an_element_name) then Result := does_element_match (destination_service_parameter, an_element_value) elseif element_path.is_equal (an_element_name) then Result := has_path (an_element_value) end end feature -- Element change set_message_id (a_message_id: like message_id) is -- Set new message id require Id_valid: a_message_id /= Void do message_id := a_message_id renew_document ensure Id_set: message_id.is_equal (a_message_id) end set_destination_service_name (a_service_name: like destination_service_name) is -- Set new service name require Name_valid: a_service_name /= Void do destination_service_name := a_service_name renew_document ensure Name_set: destination_service_name.is_equal (a_service_name) end set_destination_service_parameter (a_service_parameter: like destination_service_parameter) is -- Set new service parameter require Parameter_valid: a_service_parameter /= Void do destination_service_parameter := a_service_parameter renew_document ensure Parameter_set: destination_service_parameter.is_equal (a_service_parameter) end set_ttl (a_ttl: like ttl) is -- Set new ttl require Ttl_valid: a_ttl >= 0 do ttl := a_ttl renew_document ensure Ttl_set: ttl = a_ttl end decrease_ttl is -- Decrease ttl do ttl := ttl - 1 renew_document ensure Ttl_decreased: ttl = old (ttl) - 1 end add_path (a_path: STRING) is -- Add path require Path_valid: a_path /= Void do paths.put_last (a_path) renew_document ensure Path_set: paths.has (a_path) end feature -- Output document: P2P_XML_DOCUMENT is -- Create XML document local cached: BOOLEAN do cached := cached_document /= Void -- create document Result := Precursor if not cached then -- element MessageId Result.create_root_child_element (element_message_id, Result.namespace_empty) Result.create_content (Result.last_element, uuid_string (message_id, 0)) -- element DestSName Result.create_root_child_element (element_destination_service_name, Result.namespace_empty) Result.create_content (Result.last_element, destination_service_name) -- element DestSParam if destination_service_parameter /= Void then Result.create_root_child_element (element_destination_service_parameter, Result.namespace_empty) Result.create_content (Result.last_element, destination_service_parameter) end -- element TTL Result.create_root_child_element (element_ttl, Result.namespace_empty) Result.create_content (Result.last_element, ttl.out) -- elements Path from paths.start until paths.after loop Result.create_root_child_element (element_path, Result.namespace_empty) Result.create_content (Result.last_element, paths.item_for_iteration) paths.forth end end end feature {NONE} -- Implementation Element_message_id: STRING is "MessageId" Element_destination_service_name: STRING is "DestSName" Element_destination_service_parameter: STRING is "DestSParam" Element_ttl: STRING is "TTL" Element_path: STRING is "Path" Type_message_id: STRING is "xs:string" Type_destination_service_name: STRING is "xs:string" Type_destination_service_parameter: STRING is "xs:string" Type_ttl: STRING is "xs:unsignedInt" Type_path: STRING is "xs:anyURI" root_element_name: STRING is "RendezVousPropagateMessage" attribute_handler (root_attribute: XM_ATTRIBUTE) is -- No attributes do end element_handler (element: XM_ELEMENT) is -- Handle root child element of parsed advertisement local content: STRING do if element_message_id.is_equal (element.name) then content := element_text (element) if content.count = 2 * uuid_bytes_count + content.occurrences ('-') then parse_uuid_from_string (content, message_id, 0) end elseif element_destination_service_name.is_equal (element.name) then destination_service_name := trimmed (element.text) elseif element_destination_service_parameter.is_equal (element.name) then destination_service_parameter := trimmed (element.text) elseif element_ttl.is_equal (element.name) then content := trimmed (element.text) if content /= Void and content.is_integer then ttl := content.to_integer end elseif element_path.is_equal (element.name) then content := trimmed (element.text) if content /= Void and not content.is_empty then paths.put_last (content) end end end validate is -- Validate document and set `is_valid' do is_valid := is_valid and message_id /= Void and destination_service_name /= Void and paths.count /= 0 end initialize is -- Initialize object's data structure do Precursor create {DS_LINKED_LIST [STRING]} paths.make create message_id.make (0, uuid_bytes_count - 1) end invariant Paths_existent: paths /= Void end