¿Cuál es la mejor manera de crear HTML en código C #? [cerrado]

15

Creo que el marcado debe permanecer en el marcado y no en el código detrás.

Llegué a una situación en la que creo que es aceptable construir el HTML en el código que se encuentra detrás. Me gustaría llegar a un consenso sobre cuáles son o deberían ser las mejores prácticas.

¿Cuándo es aceptable construir html en el código detrás? ¿Cuál es el mejor método para crear este html? (ejemplo: Strings, StringBuilder, HTMLWriter, etc.)

Rodney
fuente
intente usar plantillas y marcadores de posición donde escupirá estas marcas html.
Yusubov
55
Otra opción: producir XML basado en su modelo de datos y luego usar XSLT para convertir el XML en HTML.
FrustratedWithFormsDesigner
Acabo de recibir mi aviso hoy C # / XAML para HTML5, parece prometedor y puede adaptarse a su escenario. cshtml5.com
softveda
Un problema con la ruta XSLT está en la localización. Si necesita dos idiomas, necesita dos hojas de estilo XSLT y mantenerlas paralelas. Eso es el infierno Mejor solo escribe HTML en un archivo de texto desde C #. usa String.Format y $ ".. {variable} ..." junto con WPFLocalization?
Erik

Respuestas:

12

¿Usar algo como Razor no es aplicable aquí? Porque si estás generando mucha html con un motor de visualización, puedes hacerlo mucho más fácil. También fue construido para ser usado fuera de ASP.NET.

Sin embargo, a veces eso no es lo que necesitas. ¿Ha considerado usar la clase TagBuilder que es parte de .net (mvc)? También está el HtmlWriter en System.Web.UI (para formularios web). Recomendaría uno de estos si está haciendo Controlso Html Helpers.

Daniel Little
fuente
3
+1, si necesita plantillas dentro de una maquinilla de afeitar de aplicación, es el camino a seguir. Eche un vistazo a razorengine @ nuget.org/packages/RazorEngine si necesita una gran opción para montar la maquinilla de afeitar dentro de una aplicación que no sea asp.net.
Wyatt Barnett
1
Tengo un requisito similar donde necesito generar html (un montón de él) en una biblioteca de clases. Quiero usar razor para esto, pero me cuesta entender cómo mantener archivos cshtml en un dll. ¿Cómo puede agruparse?
Yashvit
Puede pasar cualquier cadena stackoverflow.com/questions/3628895/…
Daniel Little
14

Me gustaría utilizar la agilidad paquete HTML para montar HTML y luego escribirlo en un archivo de texto.

Se emplearon muchas horas de trabajo para hacer que el paquete de agilidad HTML sea robusto y compatible con HTML.

Creo que incluso incluye una aplicación de muestra que genera HTML.

Desde la página de inicio:

Aplicaciones de muestra:

Fijación o generación de páginas. Puede arreglar una página de la manera que desee, modificar el DOM, agregar nodos, copiar nodos, bueno ... lo que sea.

Jim G.
fuente
5

Me gustaría utilizar htmltags para crear HTML.

Ejemplo:

var tag = new HtmlTag("span")
    .Text("Hello & Goodbye")
    .AddClass("important")
    .Attr("title", "Greetings")

Y luego CSQuery si quiero analizar HTML

Ejemplo:

dom.Select("div > span")
    .Eq(1)
    .Text("Change the text content of the 2nd span child of each div");
jgauffin
fuente
2

Por supuesto, existen bibliotecas, como HTML Agility Pack, que pueden ayudarlo en estos esfuerzos.

Si realmente no desea utilizar una biblioteca existente, y desea un código simple y sucio, me gusta la idea de resumir algunos de los comportamientos como se indicó en una respuesta anterior. También me gusta la idea de usar un StringBuilder subyacente, en lugar de una cadena por un par de razones:

  1. Las cadenas son menos eficientes que el generador de cadenas
  2. StringBuilder es una estructura de datos indexable,

Si no necesito un motor HTML diseñado de forma masiva, crearía una interfaz simple e intuitiva

AddLineBreak();
AddSimpleTag(string tagName);
AddSimpleTagAt(string tagName, string content, int index);
Output();
Tim C
fuente
1
La estructura de datos indexables es convincente, pero no me preocuparía demasiado por la eficiencia: codinghorror.com/blog/2009/01/…
Jim G.
1
Me he mordido algunas veces sobre la pesadez de las cadenas, especialmente las cadenas realmente grandes. Los StringBuilders son más eficientes en cuanto a memoria y procesador cuando se hacen grandes. Entonces, en una implementación como esta, donde el HTML puede ser realmente grande, comenzaría con un StringBuilder. Si hubiera una garantía de que el HTML no iba a ser muy grande, una cadena sin duda sería adecuada.
Tim C
1
Bueno, si el HTML puede ser realmente grande, entonces recomendaría el paquete de agilidad HTML. [En realidad, recomendé el paquete de agilidad HTML dos minutos antes que tú. :)]
Jim G.
1

Si termina usando solo cadenas, no olvide escapar de todos los caracteres HTML reservados en sus datos de salida.

&    &
>    >
<    &lt;
"    &quot;
'    &apos;

Sin embargo, recomiendo usar una clase o biblioteca compatible con HTML en lugar de trabajar directamente con cadenas. HTMLWriter parece un muy buen comienzo.

Mike Clark
fuente
Gracias por esta vision. Para quien sea que lea esto, esto es lo que uso para pasar los valores de una tabla de datos en una plantilla de elemento. La clave es (como sugiere Mike Clark) tener conocimiento de HTML: <asp: Button ID = "btnEdit" CssClass = "btnmaatwerksmall" runat = "server" Text = "Wijzig" OnClientClick = '<% # String.Format ("OpenChildInEnterprise (& apos; {0} & apos;, & apos; {1} & apos;, & apos; {2} & apos;); ", Eval (" Cursus "), Eval (" Omschrijving "), Eval (" Opmerking "))% > '/>
real_yggdrasil
-1

Casi dos años después de la publicación original, aquí hay una solución que me ha funcionado bien. En el documento de destino coloco lo siguiente:

<table>    
    <%:theHtmlTableMomToldYouAbout() %>    //# Where I want my rows of table data to go
</table>

la función que se llama se ve así:

    public HtmlString theHtmlTableMomToldYouAbout()
    {
        string content = "";
        HtmlString theEnvelopePlease = null;

        for (int i = 0; i < 5; i++)
        {
            content = content + "<tr><td>The Number Is: " + i + "</td></tr>";
        }
        theEnvelopePlease = new HtmlString(content);
        return theEnvelopePlease;      
    }

Y el resultado resultante en el navegador es el esperado:
El número es: 0
El número es: 1
El número es: 2
El número es: 3
El número es: 4

Cuando voy a ver la fuente, encuentro lo siguiente:

<table>
    <tr><td>The Number Is: 0</td></tr>
    <tr><td>The Number Is: 1</td></tr>
    <tr><td>The Number Is: 2</td></tr>
    <tr><td>The Number Is: 3</td></tr>
    <tr><td>The Number Is: 4</td></tr>
</table>
WebFixItMan
fuente
1
Señalaré que su solución tiene muchos de los mismos problemas con el 'contenido' como una cadena inmutable que los descritos en las publicaciones de baja puntuación a esta pregunta.
-1

¡LLAMA EN!

var html = "";
html += "<table class='colorful'>";
foreach(var item in collection) {
     html += "<tr>";
     html += "<td class='boldCell'>" + item.PropWhatever + "</td>";
     // more cells here as needed
     html += "</tr>";
}
html += "</table>";
placeholder1.InnerHtml = html;

Probablemente me rechazarán por esto, pero como ex diseñador que tuvo que ajustar HTML en el código antes de que realmente supiera mucho sobre .NET, el código anterior fue mucho más fácil de entender que los métodos que abstraen la creación de HTML. Si crees que un diseñador podría tener que modificar tu HTML, usa cadenas simples como esta.

Algo que veo que muchos desarrolladores pierden cuando escriben HTML en código es que en HTML, se permiten comillas simples o dobles para los atributos. Por lo tanto, en lugar de escapar de todas las comillas en el código (que parece no estar bien para los no iniciados), solo use comillas simples para las comillas html dentro de sus cadenas.


MULTA. Todos los que odian a los concatenantes están atacando a mi representante. Aquí está la forma 'adecuada' de hacer esto sin concatenación de cadenas, pero mantengo mi opinión de que cualquier página normal con tablas normales no presentará ningún problema de rendimiento fuera de una escala ridícula similar a Google:

var sb = new System.Text.StringBuilder();
sb.Append("<table class='colorful'>");
foreach (var item in collection)
{
     sb.Append("<tr>");
     sb.Append("<td class='boldCell'>" + item.PropWhatever + "</td>");
     // more cells here as needed
     sb.Append("</tr>");
}
sb.Append("</table>");
placeholder1.InnerHtml = sb.ToString();
Graham
fuente
3
-1 usar + para concatenar cadenas en bucles es lo peor que puede hacer.
Daniel Little
continúa: consulte stackoverflow.com/questions/3102806/…
Daniel Little el
Bueno, para empezar, usar +=dentro de un bucle de esta manera no escala en absoluto; Debido a que las cadenas son inmutables, está creando una cadena nueva cada vez que lo hace. Use un StringBuilderen su lugar.
Robert Harvey
3
¿Por qué las personas que escriben códigos horribles comparten su horrible código con otras personas?
Ramhound
3
@Ramhound ¿Qué If you think a designer might ever have to tweak your HTML, use simple strings like this.es difícil de entender? La definición de algunas personas de código horrible es la que compra milisegundos de rendimiento a costa de tomarse unos segundos para comprender completamente. Claramente, cuando anticipa que su código sea visto o mantenido por el mínimo común denominador individual, lo más seguro es que escribir un código que sea más fácil de entender o modificar siempre es mejor que el código más limpio o de mejor rendimiento.
maple_shaft