mirror of
				https://github.com/zulip/zulip.git
				synced 2025-11-04 05:53:43 +00:00 
			
		
		
		
	topic_link_util: Add support for empty topics in the backend.
Fallback links with empty topics now have correct url and text for the "general chat" topic.
This commit is contained in:
		@@ -3,6 +3,8 @@
 | 
				
			|||||||
import re
 | 
					import re
 | 
				
			||||||
import urllib.parse
 | 
					import urllib.parse
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					from zerver.models.messages import Message
 | 
				
			||||||
 | 
					
 | 
				
			||||||
invalid_stream_topic_regex = re.compile(r"[`>*&\[\]]|(\$\$)")
 | 
					invalid_stream_topic_regex = re.compile(r"[`>*&\[\]]|(\$\$)")
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					
 | 
				
			||||||
@@ -42,13 +44,6 @@ def encode_hash_component(s: str) -> str:
 | 
				
			|||||||
    return "".join(hash_replacements.get(c, c) for c in encoded)
 | 
					    return "".join(hash_replacements.get(c, c) for c in encoded)
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					
 | 
				
			||||||
def channel_topic_url(stream_id: int, stream_name: str, topic_name: str | None = None) -> str:
 | 
					 | 
				
			||||||
    link = f"#narrow/channel/{stream_id}-{encode_hash_component(stream_name.replace(' ', '-'))}"
 | 
					 | 
				
			||||||
    if topic_name:
 | 
					 | 
				
			||||||
        link += f"/topic/{encode_hash_component(topic_name)}"
 | 
					 | 
				
			||||||
    return link
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
def get_fallback_markdown_link(
 | 
					def get_fallback_markdown_link(
 | 
				
			||||||
    stream_id: int, stream_name: str, topic_name: str | None = None
 | 
					    stream_id: int, stream_name: str, topic_name: str | None = None
 | 
				
			||||||
) -> str:
 | 
					) -> str:
 | 
				
			||||||
@@ -56,15 +51,19 @@ def get_fallback_markdown_link(
 | 
				
			|||||||
    Generates the markdown link syntax for a stream or topic link.
 | 
					    Generates the markdown link syntax for a stream or topic link.
 | 
				
			||||||
    """
 | 
					    """
 | 
				
			||||||
    escape = escape_invalid_stream_topic_characters
 | 
					    escape = escape_invalid_stream_topic_characters
 | 
				
			||||||
    url = channel_topic_url(stream_id, stream_name, topic_name)
 | 
					    link = f"#narrow/channel/{stream_id}-{encode_hash_component(stream_name.replace(' ', '-'))}"
 | 
				
			||||||
    if topic_name:
 | 
					    text = f"#{escape(stream_name)}"
 | 
				
			||||||
        return f"[#{escape(stream_name)} > {escape(topic_name)}]({url})"
 | 
					    if topic_name is not None:
 | 
				
			||||||
 | 
					        link += f"/topic/{encode_hash_component(topic_name)}"
 | 
				
			||||||
 | 
					        if topic_name == "":
 | 
				
			||||||
 | 
					            topic_name = Message.EMPTY_TOPIC_FALLBACK_NAME
 | 
				
			||||||
 | 
					        text += f" > {escape(topic_name)}"
 | 
				
			||||||
 | 
					
 | 
				
			||||||
    return f"[#{escape(stream_name)}]({url})"
 | 
					    return f"[{text}]({link})"
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					
 | 
				
			||||||
def get_stream_topic_link_syntax(stream_id: int, stream_name: str, topic_name: str) -> str:
 | 
					def get_stream_topic_link_syntax(stream_id: int, stream_name: str, topic_name: str) -> str:
 | 
				
			||||||
    # If the topic name is such that it will generate an invalid #**stream>topic** syntax,
 | 
					    # If the stream/topic name is such that it will generate an invalid #**stream>topic** syntax,
 | 
				
			||||||
    # we revert to generating the normal markdown syntax for a link.
 | 
					    # we revert to generating the normal markdown syntax for a link.
 | 
				
			||||||
    if will_produce_broken_stream_topic_link(topic_name) or will_produce_broken_stream_topic_link(
 | 
					    if will_produce_broken_stream_topic_link(topic_name) or will_produce_broken_stream_topic_link(
 | 
				
			||||||
        stream_name
 | 
					        stream_name
 | 
				
			||||||
@@ -74,7 +73,7 @@ def get_stream_topic_link_syntax(stream_id: int, stream_name: str, topic_name: s
 | 
				
			|||||||
 | 
					
 | 
				
			||||||
 | 
					
 | 
				
			||||||
def get_stream_link_syntax(stream_id: int, stream_name: str) -> str:
 | 
					def get_stream_link_syntax(stream_id: int, stream_name: str) -> str:
 | 
				
			||||||
    # If the topic name is such that it will generate an invalid #**stream>topic** syntax,
 | 
					    # If the stream name is such that it will generate an invalid #**stream** syntax,
 | 
				
			||||||
    # we revert to generating the normal markdown syntax for a link.
 | 
					    # we revert to generating the normal markdown syntax for a link.
 | 
				
			||||||
    if will_produce_broken_stream_topic_link(stream_name):
 | 
					    if will_produce_broken_stream_topic_link(stream_name):
 | 
				
			||||||
        return get_fallback_markdown_link(stream_id, stream_name)
 | 
					        return get_fallback_markdown_link(stream_id, stream_name)
 | 
				
			||||||
 
 | 
				
			|||||||
@@ -68,3 +68,11 @@ class TestTopicLinkUtil(ZulipTestCase):
 | 
				
			|||||||
            get_stream_topic_link_syntax(sweden_id, "Sweden", "&a[b"),
 | 
					            get_stream_topic_link_syntax(sweden_id, "Sweden", "&a[b"),
 | 
				
			||||||
            f"[#Sweden > &a[b](#narrow/channel/{sweden_id}-Sweden/topic/.26a.5Bb)",
 | 
					            f"[#Sweden > &a[b](#narrow/channel/{sweden_id}-Sweden/topic/.26a.5Bb)",
 | 
				
			||||||
        )
 | 
					        )
 | 
				
			||||||
 | 
					        self.assertEqual(
 | 
				
			||||||
 | 
					            get_stream_topic_link_syntax(sweden_id, "Sweden", ""),
 | 
				
			||||||
 | 
					            "#**Sweden>**",
 | 
				
			||||||
 | 
					        )
 | 
				
			||||||
 | 
					        self.assertEqual(
 | 
				
			||||||
 | 
					            get_stream_topic_link_syntax(sweden_id, "Sw*den", ""),
 | 
				
			||||||
 | 
					            f"[#Sw*den > general chat](#narrow/channel/{sweden_id}-Sw*den/topic/)",
 | 
				
			||||||
 | 
					        )
 | 
				
			||||||
 
 | 
				
			|||||||
		Reference in New Issue
	
	Block a user