AlejTech/Blog/Plná kontrola nad výstupom ASPX stránky
Prejsť na navigáciu

Plná kontrola nad výstupom ASPX stránky

Plná kontrola nad výstupom ASPX stránky

Občas sa môže stať, že ASP.NET generuje do stránok html kód, ktorý vám z akéhokoľvek dôvodu nevyhovuje. Najbežnejší prípad je, ak máte jednoduchú stránku bez formulárových prvkov.

ASP.NET do nej vygeneruje <form> tag, skryté <input> tagy s ViewState a podobne. Keďže takáto stránka nikdy nebude robiť žiaden PostBack, je v nej formulár úplne navyše.

Samozrejme môžete vynechať <form runat=”server”> na aspx stránke, ale potom nemôžete použiť niektoré prvky (controls) ako GridView a podobne. Takže máme nasledovnú jednoduchú aspx stránku:

<%@ Page Language="C#" AutoEventWireup="true"  CodeFile="Default.aspx.cs" Inherits="_Default" Theme="Default" %>
<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN" "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd">
<html xmlns="http://www.w3.org/1999/xhtml" >
<head runat="server">
    <title>Generated text</title>
</head>
<body>
    <form id="form1" runat="server">
    <div id="body">
        <h1>Generated text</h1>
        <hr />
        <p>Fuscingillam in vel, iaculisis, nas et por. Cras facinia, at, arcu ero.</p>
        <p>Vestibus. Etiam eu sagittis laorem condisse at, odio. Pellent molest.</p>
        <p>Vest sem. Morbi elis nulla, erat velit. Vestas. Pellus males nibh.</p>
        <p>o congue, ipsum diam ultricitur tincidunt mollis. Vivamus nec quam.</p>
        <p>Mauristibulum dapien. Pellus. Alique. Lorem. Curabitae wisi, in augue elis mi, ipsum.</p>
    </div>
    </form>
</body>
</html>

Text je vygenerovný mojim obľúbeným generátorom náhodného textu. Takáto stránka generuje nasledovný HTML kód:

<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN" "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd">
<html xmlns="http://www.w3.org/1999/xhtml" >
<head><title>
	Generated text
</title><link href="App_Themes/default/_screen.css" type="text/css" rel="stylesheet" /></head>
<body>
    <form name="form1" method="post" action="Default.aspx" id="form1">
<div>
<input type="hidden" name="__VIEWSTATE" id="__VIEWSTATE" value="/wEPDwUJODExMDE5NzY5ZGTtNznvtVe6+eGcNbMxzilJ1RCydA==" />
</div>

    <div id="body">
        <h1>Generated text</h1>

        <hr />
        <p>Fuscingillam in vel, iaculisis, nas et por. Cras facinia, at, arcu ero.</p>
        <p>. Vestibus. Etiam eu sagittis laorem condisse at, odio. Pellent molest.</p>
        <p>Vest sem. Morbi elis nulla, erat velit. Vestas. Pellus males nibh.</p>
        <p>o congue, ipsum diam ultricitur tincidunt mollis. Vivamus nec quam.</p>
        <p>Mauristibulum dapien. Pellus. Alique. Lorem. Curabitae wisi, in augue elis mi, ipsum.</p>

    </div>
    </form>
</body>
</html>

Takže by som chcel odstrániť <form> a <input> tagy. V codebehind stránky preťažím metódu Render a upravím výsledný kód pomocou regulárnych výrazov:

public partial class _Default : System.Web.UI.Page
{
	protected override void Render(HtmlTextWriter writer)
	{
	    System.IO.StringWriter html = new System.IO.StringWriter();
	    HtmlTextWriter render = new HtmlTextWriter(html);
	    base.Render(render);

	    writer.Write(ProcessHtml(html.ToString()));

	}

	private string ProcessHtml(string html)
	{
	    html = System.Text.RegularExpressions.Regex.Replace(html, @"<form name=""form1"".*?>", string.Empty);
	    html = System.Text.RegularExpressions.Regex.Replace(html, @"</form>", string.Empty);
	    html = System.Text.RegularExpressions.Regex.Replace(html, @"<input.*?>", string.Empty);
	    html = System.Text.RegularExpressions.Regex.Replace(html, @"<div>\s*</div>", string.Empty, System.Text.RegularExpressions.RegexOptions.Singleline);
	    return html;
	}
}

Výsledný HTML kód stránky potom vyzerá takto:

<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN" "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd">
<html xmlns="http://www.w3.org/1999/xhtml" >
<head><title>
	Generated text
</title><link href="App_Themes/default/_screen.css" type="text/css" rel="stylesheet" /></head>
<body>



    <div id="body">
        <h1>Generated text</h1>
        <hr />
        <p>Fuscingillam in vel, iaculisis, nas et por. Cras facinia, at, arcu ero.</p>

        <p>. Vestibus. Etiam eu sagittis laorem condisse at, odio. Pellent molest.</p>
        <p>Vest sem. Morbi elis nulla, erat velit. Vestas. Pellus males nibh.</p>
        <p>o congue, ipsum diam ultricitur tincidunt mollis. Vivamus nec quam.</p>
        <p>Mauristibulum dapien. Pellus. Alique. Lorem. Curabitae wisi, in augue elis mi, ipsum.</p>
    </div>

</body>
</html>

Ako vidíte, pomocou metódy Render a System.IO.StringWriter objektu môžem upravovať výstup akejkoľvek stránky. Rovnako, použitím eventu Render môžem meniť výstupné html akéhokoľvek Control.

V priloženom projekte mám vytvorenú základnú triedu, ktorá je odvodená od  System.Web.UI.Page. Jej zdrojový kód je:

namespace MyWeb
{
	public class MyPage : System.Web.UI.Page
	{
	    protected override void Render(HtmlTextWriter writer)
	    {
	        System.IO.StringWriter html = new System.IO.StringWriter();
	        HtmlTextWriter render = new HtmlTextWriter(html);
	        base.Render(render);

	        ProcessHtmlEventArgs e = new ProcessHtmlEventArgs();
	        e.Html = html.ToString();
	        OnProcessHtml(e);

	        writer.Write(e.Html);
	    }

	    public event EventHandler<ProcessHtmlEventArgs> ProcessHtml;

	    protected virtual void OnProcessHtml(ProcessHtmlEventArgs e)
	    {
	        if (ProcessHtml != null)
	            ProcessHtml(this, e);
	    }
	}

	public class ProcessHtmlEventArgs : EventArgs
	{
	    public string Html;
	}
}

Túto novú triedu potom môžem používať ako base triedu pre všetky ostatné stránky, teda:

public partial class _Default : MyWeb.MyPage
{
	protected override void OnProcessHtml(WebTest.MyWeb.ProcessHtmlEventArgs e)
	{
	    e.Html = System.Text.RegularExpressions.Regex.Replace(e.Html, @"<form name=""form1"".*?>", string.Empty);
	    e.Html = System.Text.RegularExpressions.Regex.Replace(e.Html, @"</form>", string.Empty);
	    e.Html = System.Text.RegularExpressions.Regex.Replace(e.Html, @"<input.*?>", string.Empty);

	    base.OnProcessHtml(e);
	}
}

Prípadne môžem použiť aj event ProcessHtml:

protected override void OnLoad(EventArgs e)
{
    ProcessHtml += new EventHandler<WebTest.MyWeb.ProcessHtmlEventArgs>(Default_ProcessHtml);
    base.OnLoad(e);
}

void Default_ProcessHtml(object sender, WebTest.MyWeb.ProcessHtmlEventArgs e)
{
    e.Html = System.Text.RegularExpressions.Regex.Replace(e.Html, @"<form name=""form1"".*?>", string.Empty);
    e.Html = System.Text.RegularExpressions.Regex.Replace(e.Html, @"</form>", string.Empty);
    e.Html = System.Text.RegularExpressions.Regex.Replace(e.Html, @"<input.*?>", string.Empty);
}

Analogicky sa dá podobné rozšírenie zaviesť aj na akýkoľvek Control. Pochopiteľne nejde o úplne najkrajšie riešenie. Predpokladá, že sa nezmení výstup, čo sa môže napríklad aplikovaním ControlAdapter-u. Lepšie by bolo použiť ControlAdapter, alebo priamo generovať (renderovať) výstup. Ale na druhej strane je to takto rýchle a jednoduché.

Na zmenu výstupu celej stránky si tiež môžete vytvoriť HTTP Modul a zavesiť na Response.Filter vlastnú triedu. Postup nájdete na stránkach aspnet.cz . HTTP modul má obrovskú výhodu, že ho môžete pridať a odobrať do už existujúcej aplikácie. Jediná nevýhoda použitia modulu a funkcie Response.Filter je, že v nej nemáme výstupný HTML kód “naraz”, ale po častiach cez Stream. Akékoľvek globálne nahrádzanie obsahu tak neprichádza do uváhy, keďže nemáme žiadnu kontrolu nad tým, v ktorej časti sa html rozdelí

V ďalšej časti vám ukážem konkrétnu užitočnú aplikáciu tejto techniky na zmenu html výstupu celej stránky.

Príloha

ProcessHtml.zip (4kB)

Tento článok zahŕňa témy:
Page.Render, ViewState, Regular Expression, ASP.NET, codebehind, ASP, State

Komentáre (0)

pridať komentár


V komentároch môžete používať BB kód .


K tomuto článku zatiaľ nie sú žiadne komentáre. Buďte prvý. ;]
 

Poraďte sa s nami o službách, ktoré potrebujete. My vám pripravíme konkrétnu cenovú ponuku.

Kontaktujte nás

Vďaka za projekt. Z vašej strany to bolo super.

Mgr. Miroslav Helbich, PhD.
Caldera, s.r.o.