diff --git a/src/mqtt/connection/core.rs b/src/mqtt/connection/core.rs index e3d2233..934366b 100644 --- a/src/mqtt/connection/core.rs +++ b/src/mqtt/connection/core.rs @@ -1630,7 +1630,7 @@ where } else { let lru_ta = topic_alias_send.get_lru_alias(); topic_alias_send.insert_or_update(packet.topic_name(), lru_ta); - packet = packet.remove_topic_add_topic_alias(lru_ta); + packet = packet.add_topic_alias(lru_ta); } } } else if self.auto_replace_topic_alias_send { diff --git a/src/mqtt/packet/v5_0/publish.rs b/src/mqtt/packet/v5_0/publish.rs index 7223f68..7fafc2c 100644 --- a/src/mqtt/packet/v5_0/publish.rs +++ b/src/mqtt/packet/v5_0/publish.rs @@ -688,6 +688,45 @@ where // Set topic name to empty string self.topic_name_buf = MqttString::new("").unwrap(); + self.add_topic_alias(topic_alias) + } + + /// Add TopicAlias property + /// + /// This method adds a TopicAlias property to the packet properties. This + /// is required to associate a topic alias with a topic name on the server. + /// Future messages can use only the topic alias and omit the topic name. + /// This is useful for reducing packet size when sending multiple messages + /// to the same topic. + /// + /// The method removes any existing TopicAlias property before adding the new one + /// to ensure only one TopicAlias property exists. It automatically recalculates + /// the property_length and remaining_length to reflect these changes. + /// + /// # Parameters + /// + /// - `topic_alias`: The numeric topic alias to associate with the topic name + /// + /// # Returns + /// + /// The modified `GenericPublish` instance with the TopicAlias property + /// + /// # Examples + /// + /// ```ignore + /// use mqtt_protocol_core::mqtt; + /// + /// let publish_with_topic = mqtt::packet::v5_0::Publish::builder() + /// .topic_name("sensors/temperature/room1") + /// .unwrap() + /// .payload(b"23.5") + /// .build() + /// .unwrap(); + /// + /// let publish_with_alias = publish_with_topic.add_topic_alias(42); + /// // props() now contains TopicAlias property with value 42 + /// ``` + pub fn add_topic_alias(mut self, topic_alias: TopicAliasType) -> Self { // Add TopicAlias property to the end of properties let topic_alias_property = Property::TopicAlias(crate::mqtt::packet::TopicAlias::new(topic_alias).unwrap()); diff --git a/tests/connection-core-topic-alias.rs b/tests/connection-core-topic-alias.rs index 1331ff6..96d0db3 100644 --- a/tests/connection-core-topic-alias.rs +++ b/tests/connection-core-topic-alias.rs @@ -71,8 +71,8 @@ fn auto_map_topic_alias_send() { .. } = event { - // Verify topic name is empty and topic alias is 1 - if p.topic_name().is_empty() { + // Verify topic name is present and topic alias is 1 + if p.topic_name() == "topic/a" { // Check for TopicAlias property with value 1 for prop in p.props().iter() { if let mqtt::packet::Property::TopicAlias(ta) = prop { @@ -87,7 +87,7 @@ fn auto_map_topic_alias_send() { } assert!( publish_a_mapped, - "PUBLISH A should have empty topic name and TopicAlias=1" + "PUBLISH A should have valid topic name and TopicAlias=1" ); // Send QoS0 PUBLISH B @@ -109,8 +109,8 @@ fn auto_map_topic_alias_send() { .. } = event { - // Verify topic name is empty and topic alias is 2 - if p.topic_name().is_empty() { + // Verify topic name is present and topic alias is 2 + if p.topic_name() == "topic/b" { // Check for TopicAlias property with value 2 for prop in p.props().iter() { if let mqtt::packet::Property::TopicAlias(ta) = prop { @@ -125,7 +125,7 @@ fn auto_map_topic_alias_send() { } assert!( publish_b_mapped, - "PUBLISH B should have empty topic name and TopicAlias=2" + "PUBLISH B should have valid topic name and TopicAlias=2" ); {