web-dev-qa-db-fra.com

Comment concaténer plusieurs instances MvcHtmlString

J'ai des doutes sur la manière de concaténer des instances MvcHtmlString en raison de ces informations trouvées dans MSDN :

Classe MvcHtmlString Représente une chaîne codée HTML qui ne doit plus être codée

Dois-je risquer que les chaînes soient encodées en HTML deux fois lors de l'utilisation de code comme celui-ci:

var label = Html.LabelFor(model => model.Email);
var textbox = Html.TextBoxFor(model => model.Email);
var validation = Html.ValidationMessageFor(model => model.Email);

var result = MvcHtmlString.Create(
  label.ToString() + textbox.ToString() + validation.ToString());

(note: ceci est supposé aller dans une méthode d'extension HtmlHelper pour réduire la duplication de code dans les vues).

68
M4N

Votre code est correct.

Cet extrait de MSDN signifie qu'un moteur de vue de codage (tel que le moteur de vue Aspx dans .NET 4 lors de l'utilisation de <%: %> ou le moteur de vue Razor dans MVC 3) ne doit pas recoder la valeur de chaîne de l'objet.

Ainsi, par exemple:

string s = "<tag>";
var hs = MvcHtmlString.Create(s);

<%: s %>  -- outputs "&lt;tag&gt;"
<%: hs %> -- outputs "<tag>"
27
marcind

Dommage que C # ne nous permette pas de remplacer l'opérateur + ici! Que diriez-vous d'utiliser une méthode d'extension à la place?

public static MvcHtmlString Concat(this MvcHtmlString first, params MvcHtmlString[] strings)
{
    return MvcHtmlString.Create(first.ToString() + string.Concat(strings.Select(s => s.ToString())));
}

Cela pourrait probablement être optimisé, mais vous pouvez l'exécuter. Il devrait être assez trivial de prouver que cela ne double pas les chaînes de codage avec un test unitaire.

Exemple d'utilisation:

label.Concat(textbox, validation)   

Et maintenant un plug sans vergogne pour mon blog: tilisez TagBuilder ou HtmlTags pour nettoyer votre HTML

57
Ryan

Je suis allé pour cette approche:

    private static MvcHtmlString Concat(params MvcHtmlString[] items)
    {
        var sb = new StringBuilder();
        foreach (var item in items.Where(i => i != null))
            sb.Append(item.ToHtmlString());
        return MvcHtmlString.Create(sb.ToString());
    }

C'est juste une méthode utilitaire que j'utilise dans les classes avec des méthodes d'extension pour HtmlHelper.

20
miguelv

Je sais que c'est super ancien, mais une autre façon (que je trouve plus élégante) consiste à utiliser une surcharge de la méthode String Concat, dont la définition des métadonnées est

public static String Concat(params object[] args);

que, fondamentalement, ToStrings chacun des objets transmis, puis concatène les résultats et renvoie la chaîne concaténée.

Le résultat final serait donc:

var result = MvcHtmlString.Create(
    string.Concat(
        label, textbox, validation
    )
);
2
Nahuel Prieto