tests/gateway/test_slack.py::TestSlashCommandSessionIsolation::test_channel_slash_command_uses_group_session_semantics tests/gateway/test_slack.py::TestSlashCommandSessionIsolation::test_dm_slash_command_keeps_dm_session_semantics tests/gateway/test_slack.py::TestAppMentionHandler::test_app_mention_registered_on_connect tests/gateway/test_slack.py::TestSlackConnectCleanup::test_releases_platform_lock_when_auth_fails tests/gateway/test_slack.py::TestSlackConnectCleanup::test_reconnect_closes_previous_handler_to_prevent_zombie_socket tests/gateway/test_slack.py::TestSlackSocketWatchdog::test_watchdog_reconnects_when_socket_task_dies_unexpectedly tests/gateway/test_slack.py::TestSlackSocketWatchdog::test_watchdog_reconnects_when_transport_reports_disconnected tests/gateway/test_slack.py::TestSlackSocketWatchdog::test_disconnect_stops_watchdog_and_does_not_reconnect tests/gateway/test_slack.py::TestSlackSocketWatchdog::test_watchdog_cancellation_does_not_respawn tests/gateway/test_slack.py::TestSlackSocketWatchdog::test_watchdog_unexpected_exit_respawns_via_done_callback tests/gateway/test_slack.py::TestSlackSocketWatchdog::test_connect_replaces_prior_watchdog_atomically tests/gateway/test_slack.py::TestSlackSocketWatchdog::test_reconnect_refreshes_multi_workspace_state tests/gateway/test_slack.py::TestSlackSocketWatchdog::test_reconnect_lock_prevents_concurrent_reconnects tests/gateway/test_slack.py::TestSlackProxyBehavior::test_no_proxy_helper_matches_slack_hosts tests/gateway/test_slack.py::TestSlackProxyBehavior::test_resolve_slack_proxy_url_ignores_unsupported_proxy_schemes tests/gateway/test_slack.py::TestSlackProxyBehavior::test_resolve_slack_proxy_url_checks_all_slack_hosts tests/gateway/test_slack.py::TestSlackProxyBehavior::test_connect_uses_proxy_when_not_bypassed tests/gateway/test_slack.py::TestSlackProxyBehavior::test_connect_clears_proxy_when_no_proxy_matches_slack tests/gateway/test_slack.py::TestSendDocument::test_send_document_success tests/gateway/test_slack.py::TestSendDocument::test_send_document_custom_name tests/gateway/test_slack.py::TestSendDocument::test_send_document_missing_file tests/gateway/test_slack.py::TestSendDocument::test_send_document_not_connected tests/gateway/test_slack.py::TestSendDocument::test_send_document_api_error_falls_back tests/gateway/test_slack.py::TestSendDocument::test_send_document_with_thread tests/gateway/test_slack.py::TestSendDocument::test_send_document_thread_upload_marks_bot_participation tests/gateway/test_slack.py::TestSendDocument::test_send_document_retries_transient_upload_error tests/gateway/test_slack.py::TestSendPrivateNotice::test_send_private_notice_uses_ephemeral_api tests/gateway/test_slack.py::TestSendVideo::test_send_video_success tests/gateway/test_slack.py::TestSendVideo::test_send_video_missing_file tests/gateway/test_slack.py::TestSendVideo::test_send_video_not_connected tests/gateway/test_slack.py::TestSendVideo::test_send_video_api_error_falls_back tests/gateway/test_slack.py::TestBangPrefixCommands::test_bang_known_command_is_rewritten_to_slash tests/gateway/test_slack.py::TestBangPrefixCommands::test_bang_command_with_args_preserved tests/gateway/test_slack.py::TestBangPrefixCommands::test_bang_works_inside_thread tests/gateway/test_slack.py::TestBangPrefixCommands::test_bang_unknown_token_passes_through_unchanged tests/gateway/test_slack.py::TestBangPrefixCommands::test_bang_with_bot_suffix_resolves tests/gateway/test_slack.py::TestBangPrefixCommands::test_plain_slash_still_works tests/gateway/test_slack.py::TestIncomingDocumentHandling::test_pdf_document_cached tests/gateway/test_slack.py::TestIncomingDocumentHandling::test_txt_document_injects_content tests/gateway/test_slack.py::TestIncomingDocumentHandling::test_md_document_injects_content tests/gateway/test_slack.py::TestIncomingDocumentHandling::test_json_snippet_injects_content tests/gateway/test_slack.py::TestIncomingDocumentHandling::test_large_txt_not_injected tests/gateway/test_slack.py::TestIncomingDocumentHandling::test_zip_file_cached tests/gateway/test_slack.py::TestIncomingDocumentHandling::test_oversized_document_skipped tests/gateway/test_slack.py::TestIncomingDocumentHandling::test_document_download_error_handled tests/gateway/test_slack.py::TestIncomingDocumentHandling::test_image_still_handled tests/gateway/test_slack.py::TestIncomingDocumentHandling::test_video_attachment_cached tests/gateway/test_slack.py::TestIncomingDocumentHandling::test_file_shared_video_fallback_fetches_file_info tests/gateway/test_slack.py::TestIncomingDocumentHandling::test_download_failure_is_surfaced_in_message_text tests/gateway/test_slack.py::TestIncomingDocumentHandling::test_rich_text_blocks_do_not_duplicate_plain_text tests/gateway/test_slack.py::TestIncomingDocumentHandling::test_rich_text_quotes_and_lists_are_extracted tests/gateway/test_slack.py::TestIncomingDocumentHandling::test_attachments_unfurl_text_is_appended_even_when_url_is_in_message tests/gateway/test_slack.py::TestIncomingDocumentHandling::test_message_unfurl_attachments_are_skipped tests/gateway/test_slack.py::TestIncomingDocumentHandling::test_channel_routing_ignores_bot_mentions_inside_block_text tests/gateway/test_slack.py::TestIncomingDocumentHandling::test_quoted_slash_command_text_does_not_change_message_type tests/gateway/test_slack.py::TestMessageRouting::test_dm_processed_without_mention tests/gateway/test_slack.py::TestMessageRouting::test_channel_message_requires_mention tests/gateway/test_slack.py::TestMessageRouting::test_channel_mention_strips_bot_id tests/gateway/test_slack.py::TestMessageRouting::test_bot_messages_ignored tests/gateway/test_slack.py::TestMessageRouting::test_message_edits_ignored tests/gateway/test_slack.py::TestSendTyping::test_sets_status_in_thread tests/gateway/test_slack.py::TestSendTyping::test_noop_without_thread tests/gateway/test_slack.py::TestSendTyping::test_handles_missing_scope_gracefully tests/gateway/test_slack.py::TestSendTyping::test_uses_thread_ts_fallback tests/gateway/test_slack.py::TestSendTyping::test_stop_typing_clears_tracked_thread tests/gateway/test_slack.py::TestSendTyping::test_stop_typing_noop_without_tracked_thread tests/gateway/test_slack.py::TestSendTyping::test_stop_typing_handles_api_error_gracefully tests/gateway/test_slack.py::TestSendTyping::test_send_clears_status_after_final_post tests/gateway/test_slack.py::TestSendTyping::test_streaming_final_edit_clears_status tests/gateway/test_slack.py::TestSendTyping::test_streaming_intermediate_edit_keeps_status tests/gateway/test_slack.py::TestFormatMessage::test_bold_conversion tests/gateway/test_slack.py::TestFormatMessage::test_italic_asterisk_conversion tests/gateway/test_slack.py::TestFormatMessage::test_italic_underscore_preserved tests/gateway/test_slack.py::TestFormatMessage::test_header_to_bold tests/gateway/test_slack.py::TestFormatMessage::test_header_with_bold_content tests/gateway/test_slack.py::TestFormatMessage::test_link_conversion tests/gateway/test_slack.py::TestFormatMessage::test_link_conversion_strips_markdown_angle_brackets tests/gateway/test_slack.py::TestFormatMessage::test_escapes_control_characters tests/gateway/test_slack.py::TestFormatMessage::test_preserves_existing_slack_entities tests/gateway/test_slack.py::TestFormatMessage::test_strikethrough tests/gateway/test_slack.py::TestFormatMessage::test_code_block_preserved tests/gateway/test_slack.py::TestFormatMessage::test_inline_code_preserved tests/gateway/test_slack.py::TestFormatMessage::test_mixed_content tests/gateway/test_slack.py::TestFormatMessage::test_empty_string tests/gateway/test_slack.py::TestFormatMessage::test_none_passthrough tests/gateway/test_slack.py::TestFormatMessage::test_blockquote_preserved tests/gateway/test_slack.py::TestFormatMessage::test_multiline_blockquote tests/gateway/test_slack.py::TestFormatMessage::test_blockquote_with_formatting tests/gateway/test_slack.py::TestFormatMessage::test_nested_blockquote tests/gateway/test_slack.py::TestFormatMessage::test_blockquote_mixed_with_plain tests/gateway/test_slack.py::TestFormatMessage::test_non_prefix_gt_still_escaped tests/gateway/test_slack.py::TestFormatMessage::test_blockquote_with_code tests/gateway/test_slack.py::TestFormatMessage::test_bold_italic_combined tests/gateway/test_slack.py::TestFormatMessage::test_bold_italic_with_surrounding_text tests/gateway/test_slack.py::TestFormatMessage::test_bold_italic_does_not_break_plain_bold tests/gateway/test_slack.py::TestFormatMessage::test_bold_italic_does_not_break_plain_italic tests/gateway/test_slack.py::TestFormatMessage::test_bold_italic_mixed_with_bold tests/gateway/test_slack.py::TestFormatMessage::test_pre_escaped_ampersand_not_double_escaped tests/gateway/test_slack.py::TestFormatMessage::test_pre_escaped_lt_not_double_escaped tests/gateway/test_slack.py::TestFormatMessage::test_pre_escaped_gt_not_double_escaped tests/gateway/test_slack.py::TestFormatMessage::test_mixed_raw_and_escaped_entities tests/gateway/test_slack.py::TestFormatMessage::test_link_with_parentheses_in_url tests/gateway/test_slack.py::TestFormatMessage::test_link_with_multiple_paren_pairs tests/gateway/test_slack.py::TestFormatMessage::test_link_without_parens_still_works tests/gateway/test_slack.py::TestFormatMessage::test_link_with_angle_brackets_and_parens tests/gateway/test_slack.py::TestFormatMessage::test_escaping_is_idempotent tests/gateway/test_slack.py::TestFormatMessage::test_channel_mention_preserved tests/gateway/test_slack.py::TestFormatMessage::test_everyone_mention_preserved tests/gateway/test_slack.py::TestFormatMessage::test_subteam_mention_preserved tests/gateway/test_slack.py::TestFormatMessage::test_date_formatting_preserved tests/gateway/test_slack.py::TestFormatMessage::test_channel_link_preserved tests/gateway/test_slack.py::TestFormatMessage::test_message_only_code_block tests/gateway/test_slack.py::TestFormatMessage::test_multiline_mixed_formatting tests/gateway/test_slack.py::TestFormatMessage::test_markdown_unordered_list_with_asterisk tests/gateway/test_slack.py::TestFormatMessage::test_nested_bold_in_link tests/gateway/test_slack.py::TestFormatMessage::test_url_with_query_string_and_ampersand tests/gateway/test_slack.py::TestFormatMessage::test_markdown_image_does_not_create_broken_slack_link tests/gateway/test_slack.py::TestFormatMessage::test_literal_asterisks_with_spaces_are_not_treated_as_italic tests/gateway/test_slack.py::TestFormatMessage::test_emoji_shortcodes_passthrough tests/gateway/test_slack.py::TestEditMessage::test_edit_message_formats_bold tests/gateway/test_slack.py::TestEditMessage::test_edit_message_formats_links tests/gateway/test_slack.py::TestEditMessage::test_edit_message_preserves_blockquotes tests/gateway/test_slack.py::TestEditMessage::test_edit_message_escapes_control_chars tests/gateway/test_slack.py::TestEditMessageStreamingPipeline::test_edit_message_formats_streaming_updates tests/gateway/test_slack.py::TestEditMessageStreamingPipeline::test_edit_message_formats_code_and_bold tests/gateway/test_slack.py::TestEditMessageStreamingPipeline::test_edit_message_formats_blockquote_in_stream tests/gateway/test_slack.py::TestEditMessageStreamingPipeline::test_edit_message_formats_progressive_accumulation tests/gateway/test_slack.py::TestEditMessageStreamingPipeline::test_edit_message_formats_bold_italic tests/gateway/test_slack.py::TestEditMessageStreamingPipeline::test_edit_message_does_not_double_escape tests/gateway/test_slack.py::TestEditMessageStreamingPipeline::test_edit_message_formats_url_with_parens tests/gateway/test_slack.py::TestEditMessageStreamingPipeline::test_edit_message_not_connected tests/gateway/test_slack.py::TestReactions::test_add_reaction_calls_api tests/gateway/test_slack.py::TestReactions::test_add_reaction_handles_error tests/gateway/test_slack.py::TestReactions::test_remove_reaction_calls_api tests/gateway/test_slack.py::TestReactions::test_reactions_in_message_flow tests/gateway/test_slack.py::TestReactions::test_reactions_failure_outcome tests/gateway/test_slack.py::TestReactions::test_reactions_skipped_for_non_dm_non_mention tests/gateway/test_slack.py::TestReactions::test_reactions_disabled_via_env tests/gateway/test_slack.py::TestReactions::test_reactions_enabled_by_default tests/gateway/test_slack.py::TestThreadReplyHandling::test_thread_reply_without_mention_no_session_ignored tests/gateway/test_slack.py::TestThreadReplyHandling::test_thread_reply_without_mention_with_session_processed tests/gateway/test_slack.py::TestThreadReplyHandling::test_thread_reply_with_mention_strips_bot_id tests/gateway/test_slack.py::TestThreadReplyHandling::test_top_level_message_requires_mention_even_with_session tests/gateway/test_slack.py::TestThreadReplyHandling::test_no_session_store_ignores_thread_replies tests/gateway/test_slack.py::TestAssistantThreadLifecycle::test_lifecycle_event_seeds_session_store tests/gateway/test_slack.py::TestAssistantThreadLifecycle::test_message_uses_cached_assistant_thread_identity tests/gateway/test_slack.py::TestAssistantThreadLifecycle::test_assistant_threads_cache_eviction tests/gateway/test_slack.py::TestUserNameResolution::test_resolves_display_name tests/gateway/test_slack.py::TestUserNameResolution::test_falls_back_to_real_name tests/gateway/test_slack.py::TestUserNameResolution::test_caches_result tests/gateway/test_slack.py::TestUserNameResolution::test_handles_api_error tests/gateway/test_slack.py::TestUserNameResolution::test_user_name_in_message_source tests/gateway/test_slack.py::TestSlashCommands::test_compact_maps_to_compress tests/gateway/test_slack.py::TestSlashCommands::test_resume_command tests/gateway/test_slack.py::TestSlashCommands::test_background_command tests/gateway/test_slack.py::TestSlashCommands::test_usage_command tests/gateway/test_slack.py::TestSlashCommands::test_reasoning_command tests/gateway/test_slack.py::TestSlashCommands::test_native_btw_slash tests/gateway/test_slack.py::TestSlashCommands::test_native_stop_slash_no_args tests/gateway/test_slack.py::TestSlashCommands::test_native_model_slash_with_args tests/gateway/test_slack.py::TestSlashCommands::test_legacy_hermes_prefix_still_works tests/gateway/test_slack.py::TestSlashCommands::test_legacy_hermes_freeform_question tests/gateway/test_slack.py::TestMessageSplitting::test_long_message_split_into_chunks tests/gateway/test_slack.py::TestMessageSplitting::test_short_message_single_send tests/gateway/test_slack.py::TestMessageSplitting::test_send_preserves_blockquote_formatting tests/gateway/test_slack.py::TestMessageSplitting::test_send_formats_bold_italic tests/gateway/test_slack.py::TestMessageSplitting::test_send_explicitly_enables_mrkdwn tests/gateway/test_slack.py::TestMessageSplitting::test_send_does_not_double_escape_entities tests/gateway/test_slack.py::TestMessageSplitting::test_send_formats_url_with_parens tests/gateway/test_slack.py::TestReplyBroadcast::test_broadcast_disabled_by_default tests/gateway/test_slack.py::TestReplyBroadcast::test_broadcast_enabled_via_config tests/gateway/test_slack.py::TestFallbackPreservesThreadContext::test_send_image_file_fallback_preserves_thread tests/gateway/test_slack.py::TestFallbackPreservesThreadContext::test_send_video_fallback_preserves_thread tests/gateway/test_slack.py::TestFallbackPreservesThreadContext::test_send_document_fallback_preserves_thread tests/gateway/test_slack.py::TestFallbackPreservesThreadContext::test_send_image_file_fallback_includes_caption tests/gateway/test_slack.py::TestSendImageSSRFGuards::test_send_image_blocks_private_redirect_target tests/gateway/test_slack.py::TestSendImageSSRFGuards::test_send_image_fallback_preserves_thread_metadata tests/gateway/test_slack.py::TestProgressMessageThread::test_dm_toplevel_progress_uses_message_ts_as_thread tests/gateway/test_slack.py::TestProgressMessageThread::test_dm_toplevel_shares_session_when_disabled tests/gateway/test_slack.py::TestProgressMessageThread::test_channel_mention_progress_uses_thread_ts tests/gateway/test_slack.py::TestSlackReplyToText::test_slack_reply_to_text_set_on_thread_reply tests/gateway/test_slack.py::TestSlackReplyToText::test_slack_reply_to_text_none_for_top_level_message tests/gateway/test_slack.py::TestSlashEphemeralAck::test_slash_command_stashes_response_url tests/gateway/test_slack.py::TestSlashEphemeralAck::test_slash_command_without_response_url_does_not_stash tests/gateway/test_slack.py::TestSlashEphemeralAck::test_pop_slash_context_returns_and_removes tests/gateway/test_slack.py::TestSlashEphemeralAck::test_pop_slash_context_returns_none_for_no_match tests/gateway/test_slack.py::TestSlashEphemeralAck::test_pop_slash_context_discards_stale_entries tests/gateway/test_slack.py::TestSlashEphemeralAck::test_send_uses_response_url_when_context_exists tests/gateway/test_slack.py::TestSlashEphemeralAck::test_send_falls_through_without_context tests/gateway/test_slack.py::TestSlashEphemeralAck::test_send_slash_ephemeral_fallback_on_post_failure tests/gateway/test_slack.py::TestSlashEphemeralAck::test_send_slash_ephemeral_fallback_on_exception tests/gateway/test_slack.py::TestSlashEphemeralAck::test_native_slash_stashes_context_and_dispatches tests/gateway/test_slack.py::TestSlashEphemeralAck::test_legacy_hermes_slash_stashes_context tests/gateway/test_slack.py::TestSlashEphemeralAck::test_freeform_hermes_question_does_not_stash_context tests/gateway/test_slack.py::TestSlashEphemeralAck::test_concurrent_users_same_channel_isolates_contexts tests/gateway/test_slack.py::TestSlashEphemeralAck::test_no_contextvar_does_not_match_any_context