package message

import (
	"strings"
	"testing"

	"github.com/stretchr/testify/require"
)

func TestParseDirectMentionTokens_IgnoresFencedCodeBlocks(t *testing.T) {
	t.Parallel()

	content := "Please keep this literal.\n```text\n@beta-agent should stay inert\n```\n@alpha-agent is live"

	require.Equal(t, []string{"alpha-agent"}, ParseDirectMentionTokens(content))
}

func TestParseDirectMentionTokens_IgnoresInlineCodeSpans(t *testing.T) {
	t.Parallel()

	content := "Use `@beta-agent` as literal code, but wake @alpha-agent."

	require.Equal(t, []string{"alpha-agent"}, ParseDirectMentionTokens(content))
}

func TestParseDirectMentionTokens_IgnoresTildeFencedCodeBlocks(t *testing.T) {
	t.Parallel()

	content := "~~~md\n@gamma-agent should stay inert\n~~~\n@alpha-agent is live"

	require.Equal(t, []string{"alpha-agent"}, ParseDirectMentionTokens(content))
}

func TestParseDirectMentionTokens_IgnoresMixedMarkdownCodeForms(t *testing.T) {
	t.Parallel()

	content := strings.Join([]string{
		"Live @alpha-agent stays routed.",
		"`@beta-agent` is inline inert.",
		"~~~md",
		"@gamma-agent should stay inert",
		"~~~",
		"Unpaired `backtick keeps @delta-agent live.",
		"```text",
		"@epsilon-agent should stay inert",
		"```",
	}, "\n")

	require.Equal(t, []string{"alpha-agent", "delta-agent"}, ParseDirectMentionTokens(content))
}

func TestParseControlledBroadcastMode_IgnoresMarkdownCode(t *testing.T) {
	t.Parallel()

	content := strings.Join([]string{
		"`@all` should stay inert inline.",
		"~~~text",
		"@all should stay inert in tilde fence",
		"~~~",
		"```text",
		"@all should stay inert in backtick fence",
		"```",
		"Only @online should stay live.",
	}, "\n")

	mode, err := ParseControlledBroadcastMode(content)
	require.NoError(t, err)
	require.Equal(t, ChannelBroadcastModeOnline, mode)
}

func TestParseDirectMentionTokens_IgnoresBlockquotes(t *testing.T) {
	t.Parallel()

	content := strings.Join([]string{
		"> @beta-agent should stay inert",
		"@alpha-agent is live",
	}, "\n")

	require.Equal(t, []string{"alpha-agent"}, ParseDirectMentionTokens(content))
}

func TestParseDirectMentionTokens_IgnoresNestedBlockquotes(t *testing.T) {
	t.Parallel()

	content := strings.Join([]string{
		">> @beta-agent should stay inert",
		"> > @gamma-agent should stay inert",
		"@alpha-agent is live",
	}, "\n")

	require.Equal(t, []string{"alpha-agent"}, ParseDirectMentionTokens(content))
}

func TestParseDirectMentionTokens_DoesNotTreatLazyContinuationAsBlockquote(t *testing.T) {
	t.Parallel()

	content := strings.Join([]string{
		"> quoted line",
		"@alpha-agent is live without lazy continuation",
	}, "\n")

	require.Equal(t, []string{"alpha-agent"}, ParseDirectMentionTokens(content))
}

func TestParseDirectMentionTokens_BlankLineEndsQuotedRegion(t *testing.T) {
	t.Parallel()

	content := strings.Join([]string{
		"> @beta-agent should stay inert",
		"",
		"@alpha-agent is live after the blank line",
	}, "\n")

	require.Equal(t, []string{"alpha-agent"}, ParseDirectMentionTokens(content))
}

func TestParseDirectMentionTokens_RequiresWhitespaceBoundaryAfterTightBlockquotePrefix(t *testing.T) {
	t.Parallel()

	content := strings.Join([]string{
		">@beta-agent is not a blockquote marker",
		"@alpha-agent is live",
	}, "\n")

	require.Equal(t, []string{"alpha-agent"}, ParseDirectMentionTokens(content))
}

func TestParseControlledBroadcastMode_IgnoresBlockquotedAll(t *testing.T) {
	t.Parallel()

	content := strings.Join([]string{
		"> @all should stay inert",
		"@online should stay live",
	}, "\n")

	mode, err := ParseControlledBroadcastMode(content)
	require.NoError(t, err)
	require.Equal(t, ChannelBroadcastModeOnline, mode)
}

func TestParseControlledBroadcastMode_IgnoresBlockquotedOnline(t *testing.T) {
	t.Parallel()

	content := strings.Join([]string{
		"> @online should stay inert",
		"@all should stay live",
	}, "\n")

	mode, err := ParseControlledBroadcastMode(content)
	require.NoError(t, err)
	require.Equal(t, ChannelBroadcastModeAll, mode)
}

func TestParseDirectMentionTokens_SupportsUnicodeTokens(t *testing.T) {
	t.Parallel()

	content := "请 @调研专家 看一下，并让 @助手-2 跟进。"

	require.Equal(t, []string{"调研专家", "助手-2"}, ParseDirectMentionTokens(content))
}

func TestParseDirectMentionTokens_SupportsSingleSlashAlias(t *testing.T) {
	t.Parallel()

	content := "请 @helper/core 处理，普通 @helper-core 仍是独立 token，路径 a/b 不参与。"

	require.Equal(t, []string{"helper/core", "helper-core"}, ParseDirectMentionTokens(content))
}

func TestParseDirectMentionTokens_IgnoresPathLikeSlashMentionPrefix(t *testing.T) {
	t.Parallel()

	content := "路径 @helper/core/file 不应把前缀当 mention，但 @helper/core 仍有效。"

	require.Equal(t, []string{"helper/core"}, ParseDirectMentionTokens(content))
}
