ASP.NET MVC Razor görünümünde satır sonu karakterlerini <br /> ile değiştirin


241

Girdiyi kabul eden bir metin denetimi var. Daha sonra basitçe kullanarak bir görünüme bu metni işlemeye çalışıyorum:

@ Model.CommentText

Bu, herhangi bir değeri doğru bir şekilde kodlamaktadır. Ancak, satır sonu karakterleri değiştirmek istiyorum <br />ve yeni br etiketleri kodlanmış olmadığından emin olmak için bir yol bulamıyorum. HtmlString kullanmayı denedim ama henüz şansım olmadı.


1
Satır çizgilerinin \nveritabanında olduğu gibi depolandığını ve bir <br />?
— Marko

Evet - sadece görünümde \ n yerine <br /> değiştirmeye çalışıyorum.
— bkaid

Yanıtlar:


681

Kullanım CSS white-space özelliğini yerine XSS açıkları için kendini açma!

<span style="white-space: pre-line">@Model.CommentText</span>

9
@Jacob Krall - Sadece +1 vermek için giriş yaptım. Fantastik küçük numara.
— Levi Botelho

6
quirksmode.org/css/whitespace.html'nin iyi bir açıklaması var pre-line(sadece farkındaydım nowrapve pre).
— James Skemp

7
Bunu bilmiyordum. Kesinlikle benimkinden daha iyi cevap.
— Omar

39
aslında white-space: pre-wrap;daha iyi çünkü pre-linebeyaz boşlukları tek bir boşlukta gruplandırarak metninizi kirletecek.
— Chtiwi Malek

4
Ne yazık ki bu hemen hemen hiçbir e-posta istemcisinde (Office 2013 dahil) çalışmaz.
— Roger Far

115

Takip etmeyi dene:

@MvcHtmlString.Create(Model.CommentText.Replace(Environment.NewLine, "<br />"))

Güncelleme:

Bu ilgili soruya yapılanmarcind's yoruma göre , ASP.NET MVC ekibi, benzer bir şey ve<%:<%= Jilet görünümü motoru için.

Güncelleme 2:

HTML kodlamasıyla ilgili herhangi bir soruyu zararlı kullanıcı girdileriyle ilgili bir tartışmaya dönüştürebiliriz, ancak bunun yeterli bir kısmı zaten mevcuttur.

Her neyse, potansiyel zararlı kullanıcı girdilerine dikkat edin.

@MvcHtmlString.Create(Html.Encode(Model.CommentText).Replace(Environment.NewLine, "<br />"))

Güncelleme 3 (Asp.Net MVC 3):

@Html.Raw(Html.Encode(Model.CommentText).Replace("\n", "<br />"))

13
Aman tanrım, hayır. Bazıları hakkında yorum yapmaya karar verirsem ne olur <script>?
— Darin Dimitrov

4
Teşekkürler - işe yaradı. Çok yakın ama yerine çok geç veya çok geç yapmış olması gerekir. Bunu kullanarak sona erdirdim: @ MvcHtmlString.Create (Html.Encode (Model.CommentText) .Replace ("\ n", "<br />")) çünkü Environment.NewLine düzgün çalışmıyor.
— bkaid

2
\n\r\n
— Çevre.NewLine

20
MVC 3'ün yayınlanan sürümü için öneri, MvcHtmlString yerine @ Html.Raw (Html.Encode (Model.CommentText) .Replace (Environment.NewLine, "<br />")) gibi görünüyor. En azından görüntüleme için.
— James Skemp

2
Environment.NewLine "\ r \ n" yi temsil eder. Kullanıcım linux veya mac kullanarak veri girdiyse, satır aralıkları yalnızca "\ n" veya "\ r" olur. Bir yerde bunu dikkate alan bir yöntem yok mu?
— SandRock

11

Yeni satırlara bölün (çevre agnostik) ve düzenli olarak yazdırın - kodlama veya xss için endişelenmenize gerek yok:

@if (!string.IsNullOrWhiteSpace(text)) 
{
    var lines = text.Split(new[] { '\r', '\n' }, StringSplitOptions.RemoveEmptyEntries);
    foreach (var line in lines)
    {
        <p>@line</p>
    }
}

(boş girişleri kaldırmak isteğe bağlıdır)


10

Omar'ın HTML Yardımcısı olarak üçüncü çözümü:

public static IHtmlString FormatNewLines(this HtmlHelper helper, string input)
{
    return helper.Raw(helper.Encode(input).Replace("\n", "<br />"));
}

5

DRY prensibini Omar'ın çözümüne uygulayan bir HTML Yardımcısı uzantısı:

using System.Web.Mvc;
using System.Text.RegularExpressions;

namespace System.Web.Mvc.Html {
    public static class MyHtmlHelpers {
        public static MvcHtmlString EncodedReplace(this HtmlHelper helper, string input, string pattern, string replacement) {
            return new MvcHtmlString(Regex.Replace(helper.Encode(input), pattern, replacement));
        }
    }
}

Kullanımı (iyileştirilmiş normal ifade ile):

@Html.EncodedReplace(Model.CommentText, "[\n\r]+", "<br />")

Bu ayrıca, XSS güvenlik açıklarından güvenlik sağlamak için Razor View geliştiricisine daha az önem verme avantajına da sahiptir.


Jacob'un çözümü ile ilgili endişem, satır sonlarının CSS ile oluşturulmasının HTML anlambilimini kırmasıdır .


4

Bazı metinleri paragraflara bölmem gerekiyordu ("p" etiketleri), bu yüzden önceki yanıtlardaki bazı önerileri kullanarak basit bir yardımcı oluşturdum (teşekkürler çocuklar).

public static MvcHtmlString ToParagraphs(this HtmlHelper html, string value) 
    { 
        value = html.Encode(value).Replace("\r", String.Empty);
        var arr = value.Split('\n').Where(a => a.Trim() != string.Empty);
        var htmlStr = "<p>" + String.Join("</p><p>", arr) + "</p>";
        return MvcHtmlString.Create(htmlStr);
    }

Kullanımı:

@Html.ToParagraphs(Model.Comments)

0

İşaretleme manuel olarak yayan gerektirmediği için bu yöntemi tercih ederim. Bunu kullanıyorum çünkü Razor Pages'ı dizelere dönüştürüyorum ve e-posta yoluyla gönderiyorum, bu da beyaz boşluk stilinin her zaman işe yaramayacağı bir ortam.

public static IHtmlContent RenderNewlines<TModel>(this IHtmlHelper<TModel> html, string content)
{
    if (string.IsNullOrEmpty(content) || html is null)
    {
        return null;
    }

    TagBuilder brTag = new TagBuilder("br");
    IHtmlContent br = brTag.RenderSelfClosingTag();
    HtmlContentBuilder htmlContent = new HtmlContentBuilder();

    // JAS: On the off chance a browser is using LF instead of CRLF we strip out CR before splitting on LF.
    string lfContent = content.Replace("\r", string.Empty, StringComparison.InvariantCulture);
    string[] lines = lfContent.Split('\n', StringSplitOptions.None);
    foreach(string line in lines)
    {
        _ = htmlContent.Append(line);
        _ = htmlContent.AppendHtml(br);
    }

    return htmlContent;
}
Sitemizi kullandığınızda şunları okuyup anladığınızı kabul etmiş olursunuz: Çerez Politikası ve Gizlilik Politikası.
Licensed under cc by-sa 3.0 with attribution required.