Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

When the text contained in an mjml tag contains the character '<' an exception is triggered #166

Closed
qjoseph opened this issue Mar 28, 2023 · 3 comments · Fixed by #167
Closed

Comments

@qjoseph
Copy link

qjoseph commented Mar 28, 2023

When the text contained in an mjml tag contains the character '<' an exception is triggered.

Sample:

<mjml>
    <mj-body>
        <mj-text>test: &, <, >, ', \"</mj-text>
    </mj-body>
</mjml>

You should add the conversion of the '<' to '& lt;' as for the '&'

I added this condition in XmlFixer, it seems to work:

else if (span.Length >= 2 && span[0] == '<' && span[1] != '/' // not closing tag
    && !((span.Length >= 4 && span[1] == 'm' && span[2] == 'j') // ignore start tag
        || (span.Length >= 3 && span[2] == 'm' && span[3] == 'j'))) // ignore end tag
{
    if (!IsEntity(span))
    {
        sb.Append("&lt;");
    }
    else
    {
        sb.Append(first);
    }
}

@SebastianStehle what do you think?

@SebastianStehle
Copy link
Owner

You can also use custom html tags, so your fix would not work.

@qjoseph
Copy link
Author

qjoseph commented Mar 29, 2023

Oh, you're right, I have another implementation based on your xml fixer but it's a bit complex and doesn't necessarily handle all cases.

internal static string EscapeLowerThanCharacterInTags(string html)
        {
            var span = html.AsSpan();
            var result = StringBuilders.Get();

            try
            {
                for (var i = 0; i < span.Length; i++)
                {
                    if (span[i] != '<')
                    {
                        result.Append(span.Slice(i, 1));
                        continue;
                    }

                    if (i > 0 && span[i - 1] == span[i]) // same character '<'
                    {
                        result.Append("&lt;");
                        continue;
                    }

                    // find end tag
                    var indexOfEndTag = span[i..].IndexOf('>');

                    if (indexOfEndTag != -1)
                    {
                        var tag = span.Slice(i, indexOfEndTag + 1);

                        if (tag[..2] is "</" || tag[..3] is "<br")
                        {
                            result.Append(tag);
                            i += tag.Length - 1;
                        }
                        else
                        {
                            bool notATag = false;

                            if (!(tag.Trim().IndexOfAny('!', '=') != -1 && tag.Trim().Length > 3)) // not found
                            {
                                foreach (var tagCharacter in tag)
                                    if (char.IsWhiteSpace(tagCharacter) || (char.IsPunctuation(tagCharacter) && tagCharacter is not '-' or '_'))
                                    {
                                        notATag = true;
                                        break;
                                    }
                            }

                            if (notATag)
                                result.Append("&lt;");
                            else
                            {
                                result.Append(tag);
                                i += tag.Length - 1;
                            }
                        }
                    }
                    else
                        result.Append(span[i]);
                }

                return result.ToString();
            }
            finally
            {
                StringBuilders.Return(result);
            }
        }

@SebastianStehle
Copy link
Owner

Could work.

Can you:

  1. Create a PR
  2. Integrate it into this class: https://github.com/SebastianStehle/mjml-net/blob/main/Mjml.Net/XmlFixer.cs?
  3. Write a few tests?

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

Successfully merging a pull request may close this issue.

2 participants